From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from mail1-relais-roc.national.inria.fr (mail1-relais-roc.national.inria.fr [192.134.164.82]) by walapai.inria.fr (8.13.6/8.13.6) with ESMTP id p0KJiwUN001925 for ; Thu, 20 Jan 2011 20:44:58 +0100 X-IronPort-Anti-Spam-Filtered: true X-IronPort-Anti-Spam-Result: AnoBAIsfOE3RVdivkGdsb2JhbACWCTKGBAGHNlcIFQEBAQEJCQwHEQQgpiCJeoIXhGsuiFgBAQMFhUsEgV+DTYVyhh2DLQ X-IronPort-AV: E=Sophos;i="4.60,352,1291590000"; d="scan'208";a="96077656" Received: from mail-qy0-f175.google.com ([209.85.216.175]) by mail1-smtp-roc.national.inria.fr with ESMTP/TLS/RC4-MD5; 20 Jan 2011 20:44:53 +0100 Received: by qyk8 with SMTP id 8so2232518qyk.6 for ; Thu, 20 Jan 2011 11:44:52 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=gamma; h=domainkey-signature:mime-version:sender:in-reply-to:references:from :date:x-google-sender-auth:message-id:subject:to:cc:content-type; bh=oGsHPOXth/z00OWA6D0zz35GAOdrdOufXPfhRkuR6xc=; b=TjtKjD1Qth5AnHT0M65Kb7ZlUciwyDSo4g+agvho6p2tGz0O/XiYpAQRZTd5/jp1sI oyYaSGLJiXtFI2wBZOZWVGMxluW9oRKdXyVK/bPqeMi0+j2yUZv79Xys2p7zt7UydAui YAhaYjX+IpN9lGgHaH2SAKDpOEKYfYlqCzcOU= DomainKey-Signature: a=rsa-sha1; c=nofws; d=gmail.com; s=gamma; h=mime-version:sender:in-reply-to:references:from:date :x-google-sender-auth:message-id:subject:to:cc:content-type; b=YvbqPpp0arA66t2FCukLAt1tS+wXAHLWZ3JjsmTL/gxwhkMvlBnOCOyoFph5yMmPBp HPlATrwSaR51xQEc/m0O9ZwYeqyD8k/k1fc498ggU6h7V4jjjHQvQqiXBK1OCI2ohSOB 7qtOI6juBkwm1/WnD5hWo/gBoPPOnquZEaQms= Received: by 10.229.193.204 with SMTP id dv12mr2031874qcb.274.1295552692000; Thu, 20 Jan 2011 11:44:52 -0800 (PST) MIME-Version: 1.0 Sender: gabriel.scherer@gmail.com Received: by 10.229.23.139 with HTTP; Thu, 20 Jan 2011 11:44:31 -0800 (PST) In-Reply-To: References: <4d386889.027bd80a.187c.ffffbda4@mx.google.com> From: bluestorm Date: Thu, 20 Jan 2011 20:44:31 +0100 X-Google-Sender-Auth: mt_8TSDyc79MYZB4nKSO_golGBI Message-ID: To: Andrew Cc: caml-list@inria.fr Content-Type: multipart/alternative; boundary=005045015df3fe9766049a4c5d32 Subject: Re: [Caml-list] Strange syntax used in queue.ml -- The "<-" operator --005045015df3fe9766049a4c5d32 Content-Type: text/plain; charset=ISO-8859-1 An addendum for "ref" patterns. They're not a specific syntacitc sugar, but are actually genuine mutable variant types: type 'a ref = ref of mutable 'a In Caml Light (but not in OCaml), variant constructor may begin with a lowercase. "ref" (as a term) is therefore the constructor for the ref type, and can be naturally used when a pattern matching. It also appears as a function (ref : 'a -> 'a ref) because Caml Light, like Haskell but not OCaml, automatically turns constructors into functions. The ref type is defined here in the documentation: http://caml.inria.fr/pub/docs/manual-caml-light/node14.15.html On Thu, Jan 20, 2011 at 6:43 PM, bluestorm wrote: > The semantics of mutable fields and references has changed a lot (for good) > between Caml Light and Objective Caml. Beware that this code is Caml Light > specific -- and if you want to learn Caml, you should rather be using > Objective Caml, which is the implementation that is still maintained. > > In Objective Caml, only records fields are mutable. References are a > derived concept, the type 'a ref is defined as : > type 'a ref = { mutable contents : 'a } > > You change a mutable field with the syntax foo.bar <- baz (where "bar" is > a record field, and foo and baz are any expression, foo being of a record > type) > > In Caml Light, record fields are mutable, but sum type fields (variants) > are mutable as well; mutable variant fields are however not used here. See > http://caml.inria.fr/pub/docs/manual-caml-light/node4.6.html for > documentation. > > In Caml Light, a record may return a mutable location, akin to a lvalue in > C-like languages. For example, with the mutable variant > type foo = Foo of mutable int > you may write: > let set_foo (f : foo) (n : int) = > match f with > | Foo loc -> > loc <- n > > "foo <- bar" is used here to assign a value "bar" to a lvalue "foo" bound > in a mutable pattern. > > In your example, two mutable patterns are used : > | { tail = Cons(_, ref newtail) as oldtail } -> > > - oldtail is a mutable pattern denoting the mutable "tail" field of the > record > - (ref newtail) is a specific syntax, a pattern on references. It binds a > mutable pattern "newtail" corresponding to the location of the reference > > In other words, in Caml Light you can write the ":=" operator as such: > let prefix := r v = > match r with > | ref loc -> > loc <- v > > Hope that helps. > > On Thu, Jan 20, 2011 at 5:53 PM, Andrew wrote: > > Hello everyone, >> >> While browsing the Caml Light library for programming examples, I stumbled >> across the following code, taken from the Caml Light queue.ml file: >> >> type 'a queue_cell = >> Nil >> | Cons of 'a * 'a queue_cell ref >> ;; >> >> type 'a t = >> { mutable head: 'a queue_cell; >> mutable tail: 'a queue_cell } >> ;; >> >> let add x = function >> { head = h; tail = Nil as t } -> (* if tail = Nil then head = >> Nil >> *) >> let c = Cons(x, ref Nil) in >> h <- c; t <- c >> | { tail = Cons(_, ref newtail) as oldtail } -> >> let c = Cons(x, ref Nil) in >> newtail <- c; oldtail <- c >> ;; >> >> This implementation of FIFO data structures puzzles me. I get the general >> idea, to keep a pointer to the last entry in the structure, so that >> appending at the end is possible. This makes perfect sense to me. However, >> it's the syntax of how this is done that bugs me. >> >> Consider the following: >> >> | { tail = Cons(_, ref newtail) as oldtail } -> >> let c = Cons(x, ref Nil) in >> newtail <- c; oldtail <- c >> >> I have a problem with types here. By the type definition, "newtail" should >> be of type "'a queue cell", since it's retrieved using "Cons(_, ref >> newtail)" in the pattern matching: if I understand correctly, this would >> mean that "newtail" binds the value pointed by the second member of the >> "tail" record field (which is a reference). >> >> So what does the "newtail <- c" means? If I try to replace this statement >> by >> "(fun x -> x <- c) newtail", I get a "The identifier x is not mutable.", >> whereas the code sounds perfectly similar to the original variant to me. >> >> Would rewriting these few lines to read as follows mean the same? >> >> | { tail = Cons(_, newtail) as oldtail } -> >> let c = Cons(x, ref Nil) in >> newtail := c; oldtail <- c >> >> Taking the question one step further, what does the following code >> actually >> do? >> >> type t = Nil | Node of (t ref);; >> type box = {mutable field: t};; >> >> let poke = function >> | {field = Node(ref n)} -> n <- Nil >> | {field = Nil} -> () >> ;; >> >> let test = {field = Node(ref (Node(ref Nil)))};; >> poke test;; >> test;; >> >> Is it the same to write >> {field = Node(n)} -> n := Nil >> and >> {field = Node(ref n)} -> n <- Nil >> ? >> >> Even stranger: the following code returns "The value identifier a is >> unbound." >> let a = Nil;; >> a <- Nil;; (* The value identifier a is unbound. *) >> >> >> Could someone take the time to clarify the use of "<-" for me? The various >> examples here are pretty puzzling to me... >> Thanks! >> >> >> -- >> Caml-list mailing list. Subscription management and archives: >> https://sympa-roc.inria.fr/wws/info/caml-list >> Beginner's list: http://groups.yahoo.com/group/ocaml_beginners >> Bug reports: http://caml.inria.fr/bin/caml-bugs >> >> --005045015df3fe9766049a4c5d32 Content-Type: text/html; charset=ISO-8859-1 Content-Transfer-Encoding: quoted-printable An addendum for "ref" patterns. They're not a specific syntac= itc sugar, but are actually genuine mutable variant types:

=A0=A0type 'a ref =3D ref of mutable 'a

In Cam= l Light (but not in OCaml), variant constructor may begin with a lowercase.= "ref" (as a term) is therefore the constructor for the ref type,= and can be naturally used when a pattern matching. It also appears as a fu= nction (ref : 'a -> 'a ref) because Caml Light, like Haskell but= not OCaml, automatically turns constructors into functions.

The ref type is defined here in the documentation:

On Thu, Jan 20, 2011 at 6:43 PM, bluest= orm <blues= torm.dylc@gmail.com> wrote:
http://caml.i= nria.fr/pub/docs/manual-caml-light/node4.6.html=A0for documentation.

In Caml Light, a record may return a mutable location, = akin to a lvalue in C-like languages. For example, with the mutable variant=
=A0=A0type foo =3D Foo of mutable int
you may write:
=A0=A0let set_foo (f : foo)=A0(n : int) =3D
=A0=A0 =A0match = f with
=A0=A0 =A0| Foo loc ->
=A0=A0 =A0 =A0 loc <= ;- n

"foo <- bar" is used here to ass= ign a value "bar" to a lvalue "foo" bound in a mutable = pattern.

In your example, two mutable patterns are used :
<= div class=3D"im">
=A0=A0 =A0 | { tail =3D Cons(_, ref newtail) as oldta= il } ->

- oldtail is a mutable pattern denoting the mutable "tail&q= uot; field of the record
- (ref newtail) is a specific syntax, a = pattern on references. It binds a mutable pattern "newtail" corre= sponding to the location of the reference

In other words, in Caml Light you can write the ":= =3D" operator as such:
=A0=A0let prefix :=3D r v =3D
=A0=A0 =A0match r with
=A0=A0 =A0| ref loc ->
=A0= =A0 =A0 =A0loc <- v

Hope that helps.

On Thu, Jan 20, 2011 at 5:53 PM, Andrew=A0<newsgroups.fr@gmail.com>=A0wrote:

Hello everyone,

While browsing the Caml Light library for programmin= g examples, I stumbled
across the following code, taken from the Caml Li= ght=A0queue.ml=A0file:
=A0 =A0type 'a queue_cell =3D
=A0 =A0 =A0 =A0Nil
=A0 =A0 =A0| Con= s of 'a * 'a queue_cell ref
=A0 =A0;;

=A0 =A0type 'a = t =3D
=A0 =A0 =A0{ mutable head: 'a queue_cell;
=A0 =A0 =A0 =A0mu= table tail: 'a queue_cell }
=A0 =A0;;

=A0 =A0let add x =3D function
=A0 =A0 =A0 =A0{ head =3D h; tail =3D = Nil as t } -> =A0 =A0(* if tail =3D Nil then head =3D Nil
*)
=A0 = =A0 =A0 =A0 =A0let c =3D Cons(x, ref Nil) in
=A0 =A0 =A0 =A0 =A0 =A0h &l= t;- c; t <- c
=A0 =A0 =A0| { tail =3D Cons(_, ref newtail) as oldtail= } ->
=A0 =A0 =A0 =A0 =A0let c =3D Cons(x, ref Nil) in
=A0 =A0 =A0 =A0 =A0 =A0= newtail <- c; oldtail <- c
=A0 =A0;;

This implementation of= FIFO data structures puzzles me. I get the general
idea, to keep a poin= ter to the last entry in the structure, so that
appending at the end is possible. This makes perfect sense to me. However,<= br>it's the syntax of how this is done that bugs me.

Consider th= e following:

=A0 =A0 =A0| { tail =3D Cons(_, ref newtail) as oldtail= } ->
=A0 =A0 =A0 =A0 =A0let c =3D Cons(x, ref Nil) in
=A0 =A0 =A0 =A0 =A0 =A0= newtail <- c; oldtail <- c

I have a problem with types here. B= y the type definition, "newtail" should
be of type "'= a queue cell", since it's retrieved using "Cons(_, ref
newtail)" in the pattern matching: if I understand correctly, this wou= ld
mean that "newtail" binds the value pointed by the second m= ember of the
"tail" record field (which is a reference).

So what does the "newtail <- c" means? If I try to replace= this statement by
"(fun x -> x <- c) newtail", I get a = "The identifier x is not mutable.",
whereas the code sounds pe= rfectly similar to the original variant to me.

Would rewriting these few lines to read as follows mean the same?
=A0 =A0 =A0| { tail =3D Cons(_, newtail) as oldtail } ->
=A0 =A0 = =A0 =A0 =A0let c =3D Cons(x, ref Nil) in
=A0 =A0 =A0 =A0 =A0 =A0newtail = :=3D c; oldtail <- c

Taking the question one step further, what does the following code actually=
do?

=A0 =A0type t =3D Nil | Node of (t ref);;
=A0 =A0type box =3D= {mutable field: t};;

=A0 =A0let poke =3D function
=A0 =A0 =A0| {= field =3D Node(ref n)} -> n <- Nil
=A0 =A0 =A0| {field =3D Nil} -&= gt; ()
=A0 =A0;;

=A0 =A0let test =3D {field =3D Node(ref (Node(re= f Nil)))};;
=A0 =A0poke test;;
=A0 =A0test;;

Is it the same to write
=A0 = =A0{field =3D Node(n)} -> n :=3D Nil
and
=A0 =A0{field =3D Node(re= f n)} -> n <- Nil
?

Even stranger: the following code retur= ns "The value identifier a is
unbound."
=A0 =A0let a =3D Nil;;
=A0 =A0a <- Nil;; (* The val= ue identifier a is unbound. *)


Could someone take the time to cl= arify the use of "<-" for me? The various
examples here are= pretty puzzling to me...
Thanks!


--
Caml-list mailing list. = =A0Subscription management and archives:
https://sympa-roc.inria.fr/wws= /info/caml-list
Beginner's list:=A0http://groups.yahoo.com/group/ocaml_beginnersBug reports:=A0http://caml.inria.fr/bin/caml-bugs


--005045015df3fe9766049a4c5d32--