Re: Page 76 of OCaml by John Whitington ???
"Douglas Lewit [email protected] [ocaml_beginners]" <[email protected]> Fri, 25 Mar 2016 22:25:04 -0500
| Newsgroups | gmane.comp.lang.ocaml.beginners |
|---|---|
| Message-ID | <CAM0XMJRsWZw3p5mBNib97LPnJ+=G4J9zdpOiMc8JrNJ9c0vXrQ@mail.gmail.com> |
Thanks a lot Ken. Why don't you come to NEIU and teach an Ocaml class there! We could use a good functional programming professor. ( Seriously, I think it would be great for the CS majors there, including me. ) I totally understand your ref examples above. It depends really on whether the ref variable is created inside or outside the recursive function. That makes total sense. Still slightly confused about the pack function. Part of my confusion is that I've worked with "fun" before ( to create anonymous functions ) and I've used "match with" and "try with" before, but never used function before. I need some practice! I really like the head :: tail decomposition of lists in Ocaml, and those same decompositions of lists work in Python and Ruby too. Not sure if the head :: tail deconstruction can be applied to lists in Java? Maybe. ( I am a firm believer that working in one language can make a person a better programmer in other languages. Just my personal opinion about CS education. ) Thanks for the help Ken. On Fri, Mar 25, 2016 at 1:54 PM, Kenneth Miller [email protected] [ocaml_beginners] <[email protected]> wrote: > > > Inline. > > > On Friday, March 25, 2016 2:44 PM, "Douglas Lewit [email protected] > [ocaml_beginners]" <[email protected]> wrote: > > > > Well my exploration of LISP will have to wait, otherwise I'll be mediocre > at many languages rather than really good at just a few! Changing the > topic a bit, I'm really struggling with something here. If you look at the > 99 Problems in Ocaml page, there's a problem that requires you to write a > pack function that basically does this: > > pack [1; 1; 1; 1; 2; 2; 2; 2; 3; 3] ;; > > [[1; 1; 1; 1]; [2; 2; 2; 2]; [3; 3]]; > > Just when I thought I was getting good at Ocaml I found a problem that has > truly humbled me. I've written a few different solutions. Most compile > but will not produce the desired result. I looked at the proposed solution > but had a really hard time tracing through it because in some cases the > number of required arguments seems disjoint. Here's the copy and paste of > the proposed solution: > > Okay... confusion here! First off look at *rec aux current acc* ( why > can't people just call it "accumulator" to make tracing easier?! ) So this > recursive function aux ( or auxiliary ) accepts 2 arguments, "current" and > "acc", right? But then later on in the code it after the "then" statement, > it appears that aux accepts 3 arguments, *( a :: current ) acc t*. And > then later on in the code we see aux [ ] [ ] list, which again leads to the > idea that aux accepts 3 arguments, but in the declaration of aux, the aux > function accepts only 2 arguments! Okay, I am officially confused! Why is > the number of parameters changing like that. Does it have something to do > with currying or partial function application? ( But with partial function > application the number of parameters is less rather than more than the > original number of parameters.... I thought? ) > > aux does take three parameters; the (a::current) is evaluated, and is the > type of a list with head pointing to a. It's as if this were written: > let l = a::current in > aux l acc t > > The key is in knowing the semantics and syntactic sugar that function > represents. The function keyword is not the fun keyword, and there's a > reason they are spelled uniquely. Function is actually short for something > along the lines of "fun x -> match x with"; you can give it an anonymous > parameter and it will match over it. > > If anyone can enlighten me on how to trace through this mess, I would be > very grateful! > > One last question. With regard to recursive functions that create ref > variables.... are those ref variables reinitialized every time the function > is called? I imagine they should be and would be, but.... I don't know. > I'll have to experiment with that one and figure it out. > > If they are local to the scope, yes. If they are captured by the block > structure then no. Here are some examples: > let rec local_example param1 param2 param3 = > let local_ref = abc in > blah blah computation; evaluation of local_example once again > > let pack list = > let ref not_local = xyz in > let rec captures_not_local = ... > > > # let pack list = > let rec aux current acc = function > | [] -> [] (* Can only be reached if original list is empty *) > | [x] -> (x :: current) :: acc > | a :: (b :: _ as t) -> > if a = b then aux (a :: current) acc t > else aux [] ((a :: current) :: acc) t in > List.rev (aux [] [] list);; > val pack : 'a list -> 'a list list = <fun> > > > On Thu, Mar 24, 2016 at 4:05 PM, Kenneth Miller > [email protected] [ocaml_beginners] < > [email protected]> wrote: > > > LISP is awesome because it allows you to generate code that fits what you > want. > > The way I understand it is, if you're familiar with what ppx is and does, > imagine having a language that's built around making code that can fit into > things like that - when you finish a solution, you can annotate it onto > anything basically. It's like generics or type inference, but with whole > modules and data structures instead of just a single function. > > > On Thursday, March 24, 2016 5:02 PM, "Douglas Lewit [email protected] > [ocaml_beginners]" <[email protected]> wrote: > > > > Thanks Hendrik. I'll have to find that paper by Peter Landin. The > author's name is strongly familiar, but right now I can't quite place it. > My AI professor said that LISP and other functional programming languages > are great for AI, but I didn't quite get his explanation. ( And to be > fair, his explanation was pretty short and quick. ) Something about how AI > requires the manipulation of symbolic values ( as in computer algebra ) and > for that sort of thing functional programming is better suited than other > programming paradigms. > > On Thu, Mar 24, 2016 at 3:07 PM, Hendrik Boom [email protected] > [ocaml_beginners] <[email protected]> wrote: > > > On Thu, Mar 24, 2016 at 11:49:44AM -0500, Douglas Lewit [email protected] > [ocaml_beginners] wrote: > > > > > P.S. I almost forgot. Is LISP considered the great granddaddy of all > > functional programming languages? Is it correct to say that OCaml is > > descended from LISP? Thanks for the feedback. > > I'd say so, yes. > > Since you are asking about history, perhaps you'd like some: > > One of the important papers, while not explicitly about functional > programming, that liberated functional programming from LISP was > "The Next 700 Programming Languages", by Peter Landin. > > -- hendrik > > > > > > > > >