Trait

s_mach.codetools

IsDistinctTypeAlias

Related Doc: package codetools

Permalink

trait IsDistinctTypeAlias[A] extends AnyRef

Marker trait used to mark a type alias as being a distinct type alias (DTA). A DTA is an alternative to the Scala value-class (http://docs.scala-lang.org/overviews/core/value-classes.html) that never needs to box (or unbox) since type aliases are eliminated in byte code.

A DTA is always declared with a unique trait tag to make the type alias distinct in the type system. Since the DTA is a distinct type, type-classes of the DTA can be implicitly resolved. In Scala, a normal type alias would always resolve to its underlying type.

Tagging a type alias example: type Age1 = Int // implicitly[Format[Age] ] resolves to Format[Int] trait AgeTag type Age = Int with AgeTag // implicitly[Format[Age] ] is distinct from Format[Int]

Value-classes are elided by the compiler under many circumstances, but when used in any kind of generic, such as List or Option, they are emitted. To convert from a generic of the value-class type to the underlying type requires a no-op runtime call in byte code that may or may not be eliminated by downstream optimization. For collections such as List, this means a O(n) call to map simply to cast from the value-class to the underlying type. Because DTAs are simply type aliases for their underlying type the compiler can simply treat a generic of a DTA as a generic of the underlying type without any impact on runtime.

Converting the other direction for value-classes suffers from the same problem as stated above. Because DTAs require a distinct tag, the compiler can not automatically perform the downcast. Instead, implicit defs are created to support the operation as a casting operation that should be eliminated in otput byte code.

Example generic converter: implicit def ma_to_mv[M[_],V < : IsDistinctTypeAlias[A],A]( ma: M[A] ) : M[V] = ma.asInstanceOf[M[V] ]

A DTA is declared by first creating a trait tag that is used to make the DTA distinct. Next, the type alias is declared as a mix of the underlying type, the tag and the marker trait IsDistinctTypeAlias. The IsDistinctTypeAlias marker trait is used to in implicit def conversions that convert generics (such as collections) without overhead.

Full example: trait AgeTag type Age = Int with AgeTag with IsDistinctTypeAlias[Int] implicit def Age(i: Int) = i.asInstanceOf[Age]

Self Type
IsDistinctTypeAlias[A] with A
Linear Supertypes
AnyRef, Any
Ordering
  1. Alphabetic
  2. By Inheritance
Inherited
  1. IsDistinctTypeAlias
  2. AnyRef
  3. Any
  1. Hide All
  2. Show All
Visibility
  1. Public
  2. All

Value Members

  1. final def !=(arg0: Any): Boolean

    Permalink
    Definition Classes
    AnyRef → Any
  2. final def ##(): Int

    Permalink
    Definition Classes
    AnyRef → Any
  3. final def ==(arg0: Any): Boolean

    Permalink
    Definition Classes
    AnyRef → Any
  4. final def asInstanceOf[T0]: T0

    Permalink
    Definition Classes
    Any
  5. def clone(): AnyRef

    Permalink
    Attributes
    protected[java.lang]
    Definition Classes
    AnyRef
    Annotations
    @throws( ... )
  6. final def eq(arg0: AnyRef): Boolean

    Permalink
    Definition Classes
    AnyRef
  7. def equals(arg0: Any): Boolean

    Permalink
    Definition Classes
    AnyRef → Any
  8. def finalize(): Unit

    Permalink
    Attributes
    protected[java.lang]
    Definition Classes
    AnyRef
    Annotations
    @throws( classOf[java.lang.Throwable] )
  9. final def getClass(): Class[_]

    Permalink
    Definition Classes
    AnyRef → Any
  10. def hashCode(): Int

    Permalink
    Definition Classes
    AnyRef → Any
  11. final def isInstanceOf[T0]: Boolean

    Permalink
    Definition Classes
    Any
  12. final def ne(arg0: AnyRef): Boolean

    Permalink
    Definition Classes
    AnyRef
  13. final def notify(): Unit

    Permalink
    Definition Classes
    AnyRef
  14. final def notifyAll(): Unit

    Permalink
    Definition Classes
    AnyRef
  15. final def synchronized[T0](arg0: ⇒ T0): T0

    Permalink
    Definition Classes
    AnyRef
  16. def toString(): String

    Permalink
    Definition Classes
    AnyRef → Any
  17. final def wait(): Unit

    Permalink
    Definition Classes
    AnyRef
    Annotations
    @throws( ... )
  18. final def wait(arg0: Long, arg1: Int): Unit

    Permalink
    Definition Classes
    AnyRef
    Annotations
    @throws( ... )
  19. final def wait(arg0: Long): Unit

    Permalink
    Definition Classes
    AnyRef
    Annotations
    @throws( ... )

Inherited from AnyRef

Inherited from Any

Ungrouped