Skip to content

Instantly share code, notes, and snippets.

@dlwh
Forked from milessabin/gist:89c9b47a91017973a35f
Created June 16, 2012 17:16
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save dlwh/cace1fcb319fbb776f6e to your computer and use it in GitHub Desktop.
Save dlwh/cace1fcb319fbb776f6e to your computer and use it in GitHub Desktop.
Unboxed newtype in Scala?
class User
class Checkin
type Tagged[U] = { type Tag = U }
type @@[T, U] = T with Tagged[U] // Thanks to @retronym for suggesting this type alias
class Tagger[U] {
def apply[T](t : T) : T @@ U = t.asInstanceOf[T @@ U]
}
def tag[U] = new Tagger[U]
// Manual specialization needed here ... specializing apply above doesn't help
def tag[U](i : Int) : Int @@ U = i.asInstanceOf[Int @@ U]
def tag[U](l : Long) : Long @@ U = l.asInstanceOf[Long @@ U]
def tag[U](d : Double) : Double @@ U = d.asInstanceOf[Double @@ U]
def fetch[A](id: Int @@ A): A = null.asInstanceOf[A]
def tag[U](arr: Array[Int]):Array[Int @@ U] = arr.asInstanceOf[Array[Int @@ U]]
tag[User](Array(3, 4, 5)).map(_.toString) // kaboom: java.lang.ClassCastException: [I cannot be cast to [Ljava.lang.Object
@retronym
Copy link

There are few problems like this related to varargs and specialization. The front end of the compiler makes some assumptions, like that the only type that will erase to Int is, well, Int.

@retronym
Copy link

I had half a fix cobbled together, but can't find the branch right now...

@dlwh
Copy link
Author

dlwh commented Jun 16, 2012

Sure, I figured. It's a pretty cool hack. Just have to be careful with it.

I actually used it to catch a lot of bugs in a refactoring (had to have a lot of indexed ints), but then I had to undo it all once it compiled because of the class cast.

Oh well.

@retronym
Copy link

Yeah, I would really love an officially supported version for opaque type aliases. I've got the same problem -- need a bunch of manual indexing in a montecarlo setup...

@retronym
Copy link

This seems to be working in 2.10.0, although it might be more through good luck than good management.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment