Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ClassTag-based type pattern matching hides unchecked-ness #9565

Open
scabug opened this issue Nov 23, 2015 · 8 comments
Open

ClassTag-based type pattern matching hides unchecked-ness #9565

scabug opened this issue Nov 23, 2015 · 8 comments
Labels
Milestone

Comments

@scabug
Copy link

scabug commented Nov 23, 2015

A type pattern with erased components triggers an unchecked warning regarding those erased components.

With the addition of ClassTag and its use to make type patterns of abstract types actually check something again, these warnings are not emitted. Which is fine for some types, but not all ClassTag s are created equal.

def itsa[A: reflect.ClassTag](a:Any) = a match {case a: A => a}
def unsafeCoerce[A, B]: A => B = itsa{a:A=>a}

This creates a working unsafeCoerce with no unchecked warning. The argument to itsa passes the pattern because it is a Function1[_,_].

A warning when producing a ClassTag for partially-erased types would be spurious for the Array creation use case. But a warning flag for those uninterested in creating Array, or requirement of a more specific type of tag (that warns for tag creation on partially-erased types) for type-pattern matching, might be nice.

@scabug
Copy link
Author

scabug commented Nov 23, 2015

Imported From: https://issues.scala-lang.org/browse/SI-9565?orig=1
Reporter: Stephen Compall (s11001001)
Affected Versions: 2.11.7

@scabug
Copy link
Author

scabug commented Nov 23, 2015

@milessabin said:
This was discussed at the time. If you need accuracy use shapeless's Typeable.

@scabug
Copy link
Author

scabug commented Mar 5, 2017

Stephen Compall (s11001001) said:
That's fine if you are aware of this issue, but is not helpful for those who find that an implicit ClassTag in scope makes unchecked warnings go away and move on, which is exactly when the compiler ought to point out a potential complication with the solution.

@scabug
Copy link
Author

scabug commented Mar 6, 2017

@adriaanm said:
I agree it would be better to warn. How would you design a fix for this?

@scabug
Copy link
Author

scabug commented Mar 7, 2017

@milessabin said:
Something along the lines of shapeless's Typeable would do a better job here.

@S11001001
Copy link

S11001001 commented Apr 13, 2017

@adriaanm Add a type UECT ("unerased ClassTag") such that UECT <: ClassTag but not >: TypeTag. Data-wise, it would hold exactly the same data; with an abstract singleton-tagged type, it can even be an instance of trait ClassTag. The only difference versus ClassTag would be that the compiler would emit a warning when synthesizing a UECT that produces an imperfect type pattern.

Second, emit a deprecation warning when using a ClassTag for a type pattern that is not also a UECT. If no new trait is added, it's easy enough to "tag" ClassTag as a UECT, but at least then, you are explicitly declaring your intent to potentially pollute the heap. A TypeTag can also be "tagged".

So there are two warnings:

  1. when using a non-UECT for a type pattern,
  2. when synthesizing a UECT that forms an imperfect type pattern.

@S11001001
Copy link

@Blaisorblade
Copy link

Blaisorblade commented Mar 8, 2018

UECT is interesting. Some ideas in that gist were collected from Gitter discussion. Regarding shapeless Typeable, I think it's nice but invocations shouldn't be hidden.

EDIT: and should people do my same search, the current behavior is unsound (by the Java rules for unchecked warnings).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

5 participants