- Contemporary messages sorted: [ by date ] [ by thread ] [ by subject ] [ by author ] [ by messages with attachments ]

From: Michael Hanus <hanus_at_medoc.informatik.rwth-aachen.de>

Date: Wed, 18 Dec 1996 17:13:34 +0100

Dear Friends,

I wanted to avoid to start with a discussion on the concrete syntax

because I think this is a minor (of course important) point which

can be easily changed. This was also the reason why I omitted

the grammar for the concrete syntax in the first proposal since

I think it will be rewritten many times. I am more interested

in a discussion on the *concepts* of the language, and from

this point of view I want to give short answers to Manuel's remarks.

Manuel Chakravarty wrote:

*> * Why use `:' to annotate types and `:=' for equations. This seems
*

*> picky, but it is not. Haskell allows type annotations in
*

*> expressions (which is very important to resolve type ambiguities)
*

*> and `:' would clash here with the infix list constructor.
*

Interesting point. However, please note that, in a functional logic

environment, we need one more equality. In Haskell you have two

kinds of equalities: a non-strict one (equations defining functions)

and a strict one (to compare data). In a logic environment you also

need an equality to add new constraints to your data (corresponding

to unification in pure logic programming). Therefore, we have to

distinguish these equalities by different pieces of syntax.

We have used the symbol := for defining equations since this

symbol expresses the fact that the defining equations are non-symmetric

and only used from left to right.

*> * Why use lower case data constructors? The use of upper and lower
*

*> case letters in Haskell carries semantic meaning, because
*

*> constants are written in upper case and variables in lower
*

*> case. You may think that you want to reserve upper case variables
*

*> for ex. quant. variables, but you can introduce them by other
*

*> syntactic means (see Escher, for example).
*

As we already discussed in Dagstuhl, it is not necessary to use

uppercase or lowercase characters for constructor or variables,

but the programmer is free to choose what he wants. There are

also other well-known languages which do not enforce uppercase/lowercase

rules, and in this context I think it is important to give the

programmer some freedom. Maybe in the future we can not only

distinguish syntactic objects by uppercase/lowercase, but also

by colors (my xemacs already does it, and this is quite nice).

So, why this restriction if it is not necessary?

*> I think to remember that I already argued for a Haskell-like syntax at
*

*> our meeting in Dagstuhl; I don't think that my arguments have been
*

*> seriously considered so far.
*

The reason is, again, that I would like to fix the concepts first,

and afterwards the syntax.

*> A last remark: I would even step back from some additional features,
*

*> just to keep as close as possible to Haskell. As Simon said, the ideal
*

*> solution would be a mere extension of Haskell without any change to
*

*> the base language. Think about it!
*

I see here one important problem. In Haskell you define functions

by single equations, but these equations must be read in a particular

order. This works fine without free variables, but if you have to

consider free variables, it becomes difficult to consider the

order of equations. Moreover, my experience is that it is non-trivial

to understand the meaning of equations if the order is important.

For instance, it is fairly easy that the following definition

is reasonable by considering each single equation:

or True x = True

or x True = True

or False False = False

However, in order to understand the meaning of these equations,

in current functional languages, you have to understand the

pattern matching translation, i.e., these equations have the

following meaning (here I use the simple pattern matching compiler

without optimizations, from Simon's book):

or x y = case x of

True -> True

False -> case y of

True -> True

False -> case x of

True -> ERROR

False -> case y of

True -> ERROR

False -> False

After this explanation, students often have the impression that functional

languages are not the ideal of declarative programming since the order

of equations is so important.

This is one of the main differences between Curry and Haskell.

So-called uniform programs have the same meaning in Curry and

Haskell, but non-uniform programs as above have different meanings.

For instance, the valid Haskell program

f 0 = 1

f 0 = 2

is not valid in Curry. Although we can extend Curry to cover

the same sequential behavior, it is not clear to me how this

should work if non-determinism and free variables are added.

However, I am open to good proposals.

Best regards,

Michael

Received on Mi Dez 18 1996 - 17:16:14 CET

Date: Wed, 18 Dec 1996 17:13:34 +0100

Dear Friends,

I wanted to avoid to start with a discussion on the concrete syntax

because I think this is a minor (of course important) point which

can be easily changed. This was also the reason why I omitted

the grammar for the concrete syntax in the first proposal since

I think it will be rewritten many times. I am more interested

in a discussion on the *concepts* of the language, and from

this point of view I want to give short answers to Manuel's remarks.

Manuel Chakravarty wrote:

Interesting point. However, please note that, in a functional logic

environment, we need one more equality. In Haskell you have two

kinds of equalities: a non-strict one (equations defining functions)

and a strict one (to compare data). In a logic environment you also

need an equality to add new constraints to your data (corresponding

to unification in pure logic programming). Therefore, we have to

distinguish these equalities by different pieces of syntax.

We have used the symbol := for defining equations since this

symbol expresses the fact that the defining equations are non-symmetric

and only used from left to right.

As we already discussed in Dagstuhl, it is not necessary to use

uppercase or lowercase characters for constructor or variables,

but the programmer is free to choose what he wants. There are

also other well-known languages which do not enforce uppercase/lowercase

rules, and in this context I think it is important to give the

programmer some freedom. Maybe in the future we can not only

distinguish syntactic objects by uppercase/lowercase, but also

by colors (my xemacs already does it, and this is quite nice).

So, why this restriction if it is not necessary?

The reason is, again, that I would like to fix the concepts first,

and afterwards the syntax.

I see here one important problem. In Haskell you define functions

by single equations, but these equations must be read in a particular

order. This works fine without free variables, but if you have to

consider free variables, it becomes difficult to consider the

order of equations. Moreover, my experience is that it is non-trivial

to understand the meaning of equations if the order is important.

For instance, it is fairly easy that the following definition

is reasonable by considering each single equation:

or True x = True

or x True = True

or False False = False

However, in order to understand the meaning of these equations,

in current functional languages, you have to understand the

pattern matching translation, i.e., these equations have the

following meaning (here I use the simple pattern matching compiler

without optimizations, from Simon's book):

or x y = case x of

True -> True

False -> case y of

True -> True

False -> case x of

True -> ERROR

False -> case y of

True -> ERROR

False -> False

After this explanation, students often have the impression that functional

languages are not the ideal of declarative programming since the order

of equations is so important.

This is one of the main differences between Curry and Haskell.

So-called uniform programs have the same meaning in Curry and

Haskell, but non-uniform programs as above have different meanings.

For instance, the valid Haskell program

f 0 = 1

f 0 = 2

is not valid in Curry. Although we can extend Curry to cover

the same sequential behavior, it is not clear to me how this

should work if non-determinism and free variables are added.

However, I am open to good proposals.

Best regards,

Michael

Received on Mi Dez 18 1996 - 17:16:14 CET

*
This archive was generated by hypermail 2.3.0
: Mo Feb 06 2023 - 07:15:05 CET
*