From: skaller <skaller@users.sourceforge.net>
To: Jeremy Yallop <jeremy.yallop@ed.ac.uk>
Cc: Caml List <caml-list@inria.fr>
Subject: Re: [Caml-list] ANN: pattern guards
Date: Sat, 30 Jun 2007 14:09:23 +1000 [thread overview]
Message-ID: <1183176563.8849.27.camel@rosella.wigram> (raw)
In-Reply-To: <468555F9.7090005@ed.ac.uk>
On Fri, 2007-06-29 at 19:56 +0100, Jeremy Yallop wrote:
> skaller wrote:
> > On Fri, 2007-06-29 at 15:19 +0100, Jeremy Yallop wrote:
> >> I'm pleased to announce the initial release of `patterns', an OCaml
> >> extension providing general-purposes additions to pattern matching.
> >
> > I want to do this:
> >
> > match x with
> > | Y x with a=x and b=x
> > | X (y,z) with a=y and b=z
> > -> f a b
>
> Interesting. Do you want 'z' to be in scope in the guards ("a=y" etc.)
> but not in the expression ("f a b")? Or do you just generally want to
> allow or-patterns where the branches have different bindings as long as
> the expression only uses variables that are bound in every branch?
Good question. I don't know. In theory, the idea is a
'change of variables' as in a coordinate transformation, so only the
'final' variables should be in scope, i.e. 'z' would not be in scope.
In practice, a suitable syntax needs to be devised which is convenient
to use: a common case would be:
| X with x = 1
| Y x -> f x
and it would be messy to have to write the identity change of variables
in the second branch.. so I'm open to suggestions as to syntax.
> > This won't work at the moment for two reasons:
> >
> > * I assume the precedence of 'with' is the same as 'when',
> > which is not convenient
>
> Right: "with" scopes over an entire match-case, which might include
> or-patterns, just as with "when".
Which is a pain, you can't write:
(
| X
| Y x when f x
| Z x when g x
)
-> ....
[Felix allows nested 'when' clauses but not alternatives .. the latter
due to laziness on my part implementing it]
> > * the variables in the basic patterns don't agree
> >
> > The whole point of the above is to switch all the branches
> > to normalised variables. At the moment I have to write:
> >
> > match x with
> > | Y x -> f x x
> > | X (y,z) -> f y z
>
> Unless I'm mistaken you can write this as
>
> match x with
> | Y (y as z)
> | X (y,z) -> f y z
>
> Is there some more general case for which this won't work out?
Of course! See above. Conceptually you need an arbitrary
change of variables. For example:
| Polar (r, theta) with z = polar r theta
| Cartesian (x,y) with z = cartesian x y
-> f z
As far as I can see this is basically eta-expansion,
known to dummies like me as a 'wrapper function',
which for functions allows you call a function with one
set of variables with a completely different set of variables
by a standard change of variables
The idea is basically that, but 'moved' to the other
side of the -> sign in a pattern match. The above case
can of course be written:
| Polar (r, theta) -> let z = polar r theta in f z
| Cartestian (x,y) -> let z = cartesian x y in f z
but involves duplicating the call to f.
BTW: I'm writing some basic Scheme at the moment and I'm struck
by how much is lost, not having pattern matching -- yet
of course it is almost all just sugar.
BTW2: It also strikes me good syntactic design is a tradeoff
between the tensions of avoiding duplication and gratuitous
invention, retaining localisation (things should be
defined near where they're used), and modularity
(name anything complex).
So for example simple anonymous functions are good
(localisation), let/in is good (factor complexity
but retain localisation) and C++ sucks (loss of
localisation).
--
John Skaller <skaller at users dot sf dot net>
Felix, successor to C++: http://felix.sf.net
next prev parent reply other threads:[~2007-06-30 4:09 UTC|newest]
Thread overview: 7+ messages / expand[flat|nested] mbox.gz Atom feed top
2007-06-29 14:19 Jeremy Yallop
2007-06-29 18:26 ` [Caml-list] " skaller
2007-06-29 18:56 ` Jeremy Yallop
2007-06-29 19:31 ` Brian Hurt
2007-06-30 4:09 ` skaller [this message]
2007-06-30 4:44 ` Arnaud Spiwack
2007-07-03 9:29 ` Jeremy Yallop
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1183176563.8849.27.camel@rosella.wigram \
--to=skaller@users.sourceforge.net \
--cc=caml-list@inria.fr \
--cc=jeremy.yallop@ed.ac.uk \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox