[Haskell-beginners] Restrict type in phantom data-type

baa dg aquagnu at gmail.com
Fri Sep 1 18:19:40 UTC 2017


Thank you, David. It is a good seed, I'll read more about it, I used
already GADTs and type families but I don't understand them so deep.
By the way, yes, I got warning about tick and when I added it
(s/Rainy/'Rainy/) it fixed warning :)

2017-09-01 19:19 GMT+03:00 David McBride <toad3k at gmail.com>:

> The terminology for what you are looking for was phantom type.  That
> is any type that looks like this, where the a is not mentioned on the
> right hand side.
>
> data Foo a = Foo
>
> What happens with datakinds is when you write
>
> data SomeType = Foo | Bar
>
> By default there is a type SomeType and two values Foo and Bar, which
> are of kind *, which is the default.  With datakinds enabled, it
> creates two new types 'Foo, and 'Bar, which have a kind SomeType
> (instead of *).  You can replace Rainy with 'Rainy in the other code I
> gave.  It compiles either way because there is no other type Rainy, so
> it assumes you must have meant 'Rainy.
>
> As for type families, what you have there are called open type
> families.  There is also a closed type families variant that prevents
> more instances of the type family from being declared by the library
> user.  It would look like this:
>
> data Sunny
> data Rainy
>
> type family Night a where
>   Night Sunny = SunnyNight
>   Night Rainy = RainyNight
>
> You could still write the following, which would not work in
> datakinds, but at least there is no constructor that you could use
> that would satisfy it other than the ones listed in the type family.
>
> impossibleDay2 :: Day ()
> impossibleDay2 = undefined
>
> There may be more to this than I know, but I think that about covers it.
>
> On Fri, Sep 1, 2017 at 11:23 AM, Baa <aquagnu at gmail.com> wrote:
> > I pereputal emails.
> > ---
> >
> > David, hello!
> >
> > 1. Is it the same/different as:
> >
> >   data family Day a
> >   data Sunny
> >   data Rainy
> >   data instance Day Sunny = SunnyDay deriving Show
> >   data instance Day Rainy = RainyDay deriving Show
> >
> >   ..and here you can not create `Day Int` object because no `Day Int`
> >   constructor (but you can create such constructor)
> >
> > ? Or in case with type families there is possibility to extend it to
> > `Day Int` and in case with DayaKinds it's totally impossible?
> >
> > 2. I read somewhere (on forums) that restrictions on data types... I
> > don't remember exactly, but something like they are not real
> > restrictions or are related to old extension which is/will be
> > deprecated. I'm not sure. Also, I'm not sure is it - in your example -
> > restriction (constraint) or something else. Am I wrong?
> >
> >> This is maybe edging toward haskell-cafe territory, but you can
> >> definitely do this in haskell.
> >>
> >> {-# LANGUAGE DataKinds, KindSignatures #-}
> >>
> >> data DayType = Sunny | Rainy
> >>
> >> data Day (a :: DayType) = Day
> >>
> >>
> >> sunnyDay :: Day Sunny
> >> sunnyDay = Day
> >>
> >> rainyDay :: Day Rainy
> >> rainyDay = Day
> >>
> >> -- impossibleDay :: Day ()
> >> -- impossibleDay = Day
> >>
> >> On Fri, Sep 1, 2017 at 10:18 AM, Baa <aquagnu at gmail.com> wrote:
> >> > Hello, List!
> >> >
> >> > For example, I have specialized (right nameis phantom?) type:
> >> >
> >> >   data Day a = Day { ... no `a` here }
> >> >   data Sunny
> >> >   data Rainy
> >> >
> >> >   joyToday :: Day Sunny -> IO ()
> >> >   joyToday day = ...
> >> >
> >> >   melancholyToday :: Day Rainy -> IO ()
> >> >   melancholyToday day = ...
> >> >
> >> > And I can create (in spite of that it's phantom) some day:
> >> >
> >> >   let day1 = Day {...} :: Day Sunny
> >> >   joyToday day1
> >> >
> >> > but no problem to create `Day Int`, `Day Char`, etc which is
> >> > pointless actually (sure "creator"-function can be exported from the
> >> > module only, but I'm talking about type-level solution).
> >> >
> >> > I know that constraints (`... =>`) on data types are
> >> > redundant/removed from the language. And I'm not sure how it's
> >> > possible to restrict that parameter `a` (I know that it's possible
> >> > to Java/C++/Perl6 (not sure), some other languages but how to add
> >> > such restriction in Haskell? IMHO type families can help but I'm
> >> > not sure how it will look (Sunny, Rainy are "nullary" type, so...).
> >> >
> >> > Is it possible for Haskell too?
> >> >
> >> > ===
> >> > Best regards, Paul
> >> > _______________________________________________
> >> > Beginners mailing list
> >> > Beginners at haskell.org
> >> > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners
> >> _______________________________________________
> >> Beginners mailing list
> >> Beginners at haskell.org
> >> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners
> >
> > _______________________________________________
> > Beginners mailing list
> > Beginners at haskell.org
> > http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners
> _______________________________________________
> Beginners mailing list
> Beginners at haskell.org
> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.haskell.org/pipermail/beginners/attachments/20170901/ca544c86/attachment.html>


More information about the Beginners mailing list