Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does Haskell force data constructor's first letter to be upper case?

Tags:

Give an ugly example:

data Bighead = Big  little = 1   f1 = little :: Int  f2 = Big :: BigHead 

In my opinion:

f1 and f2 all point to some data. the only different of (little and Big) is little has a piece of code to do evaluation. but Big doesn't.

They all have a rewritable body, little can be transformed from a collection of data to a result, and Big is just don't do the last step --- it always holds this data forms (but recursively they can be evaluated).

But in syntax form, they are almost the same: can be applied, can be evaluated.

One big deal may be that functions can't alter its applied params, but data can do.

Is this the only reason that Haskell treats data and function's names differently?

Call for analysis :-)

edit: some more pads

data A = B Int 

type of B:

B :: Int -> A  b :: Int -> A  b = B  
like image 887
wuxb Avatar asked Jun 04 '11 15:06

wuxb


People also ask

Is Haskell case sensitive?

Haskell is a case-sensitive programming language because functions must begin with capital letters. By contrast, types must start with an upper case letter. However, it is essential to note that in Haskell, the capitalization of the identifier usually encodes information about semantics.

What does () mean in Haskell?

() is very often used as the result of something that has no interesting result. For example, an IO action that is supposed to perform some I/O and terminate without producing a result will typically have type IO () .

How do you assign a type in Haskell?

Haskell has three basic ways to declare a new type: The data declaration, which defines new data types. The type declaration for type synonyms, that is, alternative names for existing types. The newtype declaration, which defines new data types equivalent to existing ones.

How do you convert string to uppercase in Haskell?

You need to use map (map toUpper) . This is because you have [String] instead of String . i.e. map toUpper capitalises a String, by making each letter uppercase, so map (map toUpper) capitalises each String in a list of Strings.


1 Answers

From the Haskell 98 Language we see the core distinction in identifier tokens in Haskell:

varid   ->   (small {small | large | digit | ' })<reservedid> conid   ->   large {small | large | digit | ' } 

That is, the language fundamentally distinguish variable names ("varid") from constructor names ("conid"), at all levels of the language (both value and type variables and constructors). So clearly, Haskell distinguishes identifiers into two main namespaces (well, there are others, if you count modules and classes), but two primary ones, those that begin with a lower-case letter (variable identifiers) and those that begin with an upper-case letter (constructor identifiers).

So, given that we do distinguish constructors from variables, the question is "why?".

Reading types

One plausible argument is that it makes it very easy to spot parameters in types (e.g. polymorphic types).

Pattern matching

Secondly, and more importantly, we have uniform syntax for data construction and deconstruction (pattern matching). Whenever you see an upper case identifier in a pattern,

case x of    Foo y z -> ... 

You know that Foo is a data structure being taken apart and its components named. Correspondingly, whenever you see an upper case identifier in an expression,

g (f (Foo 1 2) 

you know that f is receiving a newly built Foo data type with two arguments.

So, since constructors (both type and value) are so important in the language, this simple restriction to upper case identifiers makes it much easier for a human to see what is going on in a piece of code. In some ways upper case letters make up for the lack of other syntactic noise in the language, as an aid to the reader.


Namespaces

There are six kinds of names in Haskell : those for variables and constructors denote values; those for type variables, type constructors, and type classes refer to entities related to the type system; and module names refer to modules. There are two constraints on naming:

Names for variables and type variables are identifiers beginning with lowercase letters or underscore; the other four kinds of names are identifiers beginning with uppercase letters. An identifier must not be used as the name of a type constructor and a class in the same scope. These are the only constraints; for example, Int may simultaneously be the name of a module, class, and constructor within a single scope.

Haskell B

In Haskell B, constructors and variables could use either case.

like image 54
Don Stewart Avatar answered Jan 11 '23 14:01

Don Stewart