synonym type not allowed

Ron Wichers Schreur ronny@cs.kun.nl
Wed, 17 Dec 1997 22:58:28 +0100


Arjan van IJzendoorn wrote (to the Clean discussion list):

> [instances of synonym types]
>   The latest versions of Haskell support the "newtype"-construct.
>   I'm not completely sure about the syntax:
>
>   newtype MyType = (Int, Real)
>
>   Now you have to use a "fake" constructor MyType whenever you want
>   to construct a value of type MyType, e.g. MyType (3, 5.0). So, in
>   a way the line of code defines a type with one constructor with
>   one (strict) argument.

>   This can, of course, also be done in Clean. However, the advantage
>   of the special construct is that the compiler does not generate
>   code for the constructor applications. In other words, you don't
>   pay for constructing or breaking-down values of this type.

Haskell's newtype construct can be emulated in Clean by defining a 
record type with one strict field and a macro for construction/
destruction:

    :: MyType = {myType :: !(Int, Real)}
    MyType value :== {myType=value}

    f :: MyType -> (Int, Real)
    f (MyType value)
        =   value

    Start
        =   f (MyType (1,2.0))

In this example there's no overhead, the Clean compiler generates
the same code as it does for

    :: MyType :== !(Int, Real)

    f :: MyType -> (Int, Real)
    f value
        =   value

    Start
        =   f (1,2.0)

[Some overhead may be introduced in a few other cases. For example,
 small integers are shared in the heap. If you pack the integer in
 a record this sharing will be lost. Also there's a overhead if
 the type for which you define a newtype is itself a record with
 strict elements. This is the situation for the current Clean
 compiler (version 1.2).]

You can of course define your own instances for MyType. In fact,
you ofteh *have* to define instances, for example

    :: MyInt = {myInt :: !Int}
    MyInt value :== {myInt=value}

    instance + MyInt where
        (+) :: MyInt  MyInt -> MyInt
        (+) (MyInt a) (MyInt b)
            =   MyInt (a+b)

Apart from a lot of typing, the MyInt abstraction will cost you
an extra call for every (+). I think this is also true when
you use newtype in Haskell.


Cheers,

Ronny Wichers Schreur