i see that "my-list  (rest (rest my-list))" is in a let section.  That
seems like the scope would mean we are talking about a different my-
list.

On Jan 11, 1:19 pm, e <evier...@gmail.com> wrote:
> that's awesome, and I hope it helps others, too.  Thanks for starting
> with python.
>
> This gets to my question perfectly.  Why is your code "my-list
> (rest (rest my-list)) " legal?
> I wouldn't have even thought to try that because, in essence, you are
> changing my-list.  I mean, I know how persistence works.  You are just
> reassigning what you think of as the start of my-list, and if no one
> else is looking at the old version then it can get gc'd.  I guess I
> just assumed it would be harder some how.
>
> how do people feel about the list comprehension thing I did?
>
> seems like:
> [my-list (for [x some-list] [x])]
>
> is simpler to understand than:
> [my-list (vec (map vector some-list))]
>
> The former is just like math.  says, "give me a list of '[x]' for each
> element 'x' in some-list"
> The second says, "apply the vector operation to each element of some-
> list and then make a vector of those."  seems lower level, more
> rudimentary.
>
> Thanks for all the help.  This is great fun.
>
> On Jan 11, 12:07 pm, James Reeves <weavejes...@googlemail.com> wrote:
>
> > Thinking functionally is hard when you're used to programming
> > imperatively. So instead of leaping straight into Clojure, lets stick
> > with Python for the time being.
>
> > So let's take your Python code:
>
> > def msort(someList):
> >   myList = [[x] for x in someList]
> >   while len(myList) > 1:
> >     l1 = myList.pop(0)
> >     l2 = myList.pop(0)
> >     listmerge = some_merge_function(l1, l2)
> >     myList.append(listmerge)
> >   return myList[0]
>
> > (I'm assuming you meant msort(someList) and not msort(myList))
>
> > Remove all functions and methods that change their arguments, and
> > replace them with equivalent assignments:
>
> > def msort(someList):
> >   myList = [[x] for x in someList]
> >   while len(myList) > 1:
> >     l1 = myList[0]
> >     l2 = myList[1]
> >     myList = myList[2:]
> >     listmerge = some_merge_function(l1, l2)
> >     myList = myList + [listmerge]
> >   return myList[0]
>
> > Next we need to turn the while loop into a recursive function. We can
> > do this by identifying what the while loop changes (myList), and then
> > using that as the function's input and output:
>
> > def msort(someList):
> >   myList = [[x] for x in someList]
> >   def recursive_loop(myList)
> >     if len(myList) > 1:
> >       l1 = myList[0]
> >       l2 = myList[1]
> >       myList = myList[2:]
> >       listmerge = some_merge_function(l1, l2)
> >       myList = myList + [listmerge]
> >       myList = recursive_loop(myList)
> >       return myList
> >     else:
> >       return myList
> >   return recursive_loop(myList)[0]
>
> > Once you've replaced mutable functions and methods with assignments,
> > and replaced loops with recursive functions, you can convert your code
> > into Clojure:
>
> > (defn msort [some-list]
> >   (let
> >     [my-list (vec (map vector some-list))
> >      recursive-loop
> >       (fn [my-list]
> >         (if (> (count my-list) 1)
> >           (let [l1         (my-list 0)
> >                 l2         (my-list 1)
> >                 my-list    (rest (rest my-list))
> >                 list-merge (some-merge-function l1 l2)
> >                 my-list    (conj my-list listmerge)
> >                 my-list    (recursive-loop my-list)]
> >             my-list)
> >           my-list))]
> >     ((recursive-loop my-list) 0)))
>
> > Now we have a functional program, it's time to start taking advantage
> > of all the nice Clojure functions and macros. Let's start with the
> > loop/recur form, which we can use to replace the recursive-loop
> > function:
>
> > (defn msort [some-list]
> >   (loop [my-list (vec (map vector some-list))]
> >     (if (> (count my-list) 1)
> >       (let [l1         (my-list 0)
> >             l2         (my-list 1)
> >             my-list    (rest (rest my-list))
> >             list-merge (some-merge-function l1 l2)
> >             my-list    (conj my-list listmerge)]
> >         (recur my-list))
> >       (my-list 0))))
>
> > Clojure also supports destructuring binding in let forms, so lets use
> > that:
>
> > (defn msort [some-list]
> >   (loop [my-list (vec (map vector some-list))]
> >     (if (> (count my-list) 1)
> >       (let [[l1 l2 & my-list] my-list
> >             list-merge       (some-merge-function l1 l2)
> >             my-list          (conj my-list list-merge)]
> >         (recur my-list))
> >       (my-list 0))))
>
> > And we can use rest to check if the list has more than one attribute:
>
> > (defn msort [some-list]
> >   (loop [my-list (vec (map vector some-list))]
> >     (if (rest my-list)
> >       (let [[l1 l2 & my-list] my-list
> >             list-merge       (some-merge-function l1 l2)
> >             my-list          (conj my-list list-merge)]
> >         (recur my-list))
> >       (first my-list))))
>
> > This could be neatened up a bit, but that's basically a functional
> > version of your algorithm.
>
> > - James
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"Clojure" group.
To post to this group, send email to clojure@googlegroups.com
To unsubscribe from this group, send email to 
clojure+unsubscr...@googlegroups.com
For more options, visit this group at 
http://groups.google.com/group/clojure?hl=en
-~----------~----~----~----~------~----~------~--~---

Reply via email to