3

The following example is from "A gentle introduction to Haskell 98" by Hudak, Peterson and Fasel:

data Point a = Pt a a

What is this `Pt'? Where does it come from? What does it mean? Has it been defined previously, or are we defining it here? It appears suddenly in the text, has not been mentioned before, and a google for "Pt Haskell" returns Haskell documentation in Portugese ;-)

Edit: thanks to the reply from @unhammer, I now see that this answer to another question explains the problem really well: here

January
  • 16,320
  • 6
  • 52
  • 74
  • It might help to understand your confusion if you explained why the question is about `Pt` and not about `False` or `Green` from the previous examples in that section. – Michał Politowski Nov 29 '17 at 10:44
  • I see these values as a kind of `enum` from C: explicitly giving the possible values, so a variable of that type can take a value `Green` or `False`. I can write `let x=Green` and x will be of type `Color`. – January Nov 29 '17 at 10:59
  • 1
    Possible duplicate of [Haskell Type vs Data Constructor](https://stackoverflow.com/questions/18204308/haskell-type-vs-data-constructor) – Michał Politowski Nov 29 '17 at 12:35
  • So this is not a bad intuition, non-nullary data constructors simply generalize it so that eg. `let x=Pt Green Red` will give you an x of type `Point Color`. – Michał Politowski Nov 29 '17 at 12:40
  • yeah, but then, writing `let x=Pt` is valid, but then `x` is not of type `Point`, but rather `a -> a -> Point a`. The crucial thing was to see that "Red" is also not a value, but a data constructor returning the value "Red". Can "Red" be defined in such a way that it returns "FF0000" rather than "Red"? – January Nov 29 '17 at 14:39
  • Then I think that even more crucial will be to see that a data constructor **is** a value. That Red is a value and so is Pt (one is a value of type `Color`, the other of type `a -> a -> Point a`, as good a type as any). – Michał Politowski Nov 29 '17 at 14:48
  • Ah. If that is literally true (data constructor is a value), then I did not understand anything after all. Back to the drawing board then. (Unless you mean something meaningless like "everything is a value when you get to the bottom of it", but I think you mean "it is a value as opposed to, say, type constructor") – January Nov 30 '17 at 12:33
  • I mean you can distinguish the `Red` data constructor as a syntactic element of a program (a kind of expression) from the abstract value **Red** it evaluates to. But (by the definition in this example) it can only evaluate to this one specific value of the **Color** type. And similarly a `Pt` expression - in a program containing the `data Point a = Pt a a` definition - will evaluate to a specific value of a function type denoted by the type expression `a -> a -> Point a` (or `b -> b -> Point b`, or ...). – Michał Politowski Dec 01 '17 at 11:02

1 Answers1

6

The Pt is a name that you yourself make up. You use it to create a new Point.

λ> data Point a = Pt a a
λ> let p = Pt 1 2
λ> :t p
p :: Num a => Point a

(For these single-constructor data's, you'll also often see them named the same as the type, like data Point a = Point a a.)

unhammer
  • 4,306
  • 2
  • 39
  • 52
  • Lovely. But weird. But lovely. Thank you. Also, now the rest of the para makes sense. – January Nov 29 '17 at 11:00
  • What's weird about it? (Unless you are referring to using the same name as both the type constructor and data constructor. Yeah, that takes some getting used to.) – chepner Nov 29 '17 at 12:10
  • Because we do not define Pt (not explicitly), we only name it. When you think about it, it is logical, but it is a leap from simply enumerating possible values of a type (yes, I do understand now that in an enumerative type definition these are not "values" but data constructors returning a single data point). – January Nov 29 '17 at 14:36
  • 5
    @January Indeed, the Haskell data type definition notation is compact but can slightly confuse beginners -- here on SO it's frequent to see such confusion. If you prefer, you can turn on the `GADTSyntax` extension and use the more verbose notation `data Point a where Pt :: a -> a -> Point a` where you explicitly provide a type for `Pt`, as if it were a function signature. This is 100% equivalent to the compact one, and can be used for multiple constructors as well. I think this syntax is more clear with beginners (even if they did not read a tutorial, yet). – chi Nov 29 '17 at 16:36
  • This is, indeed, more logical. Makes perfect sense. I find I don't have problems with the logic of the language itself, but rather with weird notations, shorthands and syntax sugar – January Nov 30 '17 at 12:38
  • I am a beginner so this is all quite confusing still. Why can you wriite `let p = Pt 1 2`, without Pt being defined in any concrete way? `Pt a a` is a data constructor so it should yield a value. Is it not necessary to define how this value is generated? – evianpring Aug 02 '19 at 00:17
  • @evianpring if you've earlier said `data Point a = Pt a a` then you have defined `Pt` as concretely as you can (while still having that type). I guess the closest thing in C would be a `struct Pt{void* x; void* y;}` although the Haskell code also makes sure the `x` and `y` fields are of the same type. When you `let p = Pt 1 2` and evaluate `p`, you could imagine Haskell allocating such a C struct with pointers to two ints – unhammer Aug 02 '19 at 09:15