Re: Let bindings and immutability

2015-02-12 Thread Luc Préfontaine
Think about values first, symbols after. Symbols are accessory, not values, values are the only things that exist at runtime. Symbols are only there for you poor human (I include myself in this statement) to grasp roughly what is going on by tracking intermediate values with names. The names

Re: Let bindings and immutability

2015-02-11 Thread Ben Wolfson
The multiple-binding form of let can be recursively transformed into nested lets: (let [name1 value1 name2 value2 ... name value] body) (let [name1 value1] (let [name2 value2] ... (let [name value] body))) All you're doing with your let form is shadowing the name; there's no mutation. If

Re: Let bindings and immutability

2015-02-11 Thread Ambrose Bonnaire-Sergeant
Local bindings are immutable. Your example demonstrates lexical shadowing of bindings. This is an equivalent program semantically. (let [x 1 x_1 (inc x) x_2 (inc x_1) x_3 (inc x_2)] x_3) By the rules of lexical scoping, you cannot access the first `x` but it is never

Re: Let bindings and immutability

2015-02-11 Thread Herwig Hochleitner
2015-02-12 3:06 GMT+01:00 gvim gvi...@gmail.com: That explains it but I think Clojure's syntax is misleading here. Without knowledge of this magic the mind doesn't readily translate: In some other lisps, clojure's let is called let* for this reason. Their let binds only in parallel, similar

Re: Let bindings and immutability

2015-02-11 Thread Justin Smith
(let [x 0 f #(println x) x 1 g #(println x) x 2] (f) (g) x) there is no mutation of x, only scope shadowing hiding the other binding. Most functional languages (all that I know) allow shadowing. -- You received this message because you are subscribed to the

Re: Let bindings and immutability

2015-02-11 Thread gvim
On 12/02/2015 01:53, Ben Wolfson wrote: The multiple-binding form of let can be recursively transformed into nested lets: (let [name1 value1 name2 value2 ... name value] body) (let [name1 value1] (let [name2 value2] ... (let [name value] body))) All you're doing with your let form is

Re: Let bindings and immutability

2015-02-11 Thread Herwig Hochleitner
I think that, from a user perspective, the important difference from mutation to shadowing is, that outer x is available even in the inner context, if captured by a closure. Likewise, a second thread, that runs an outer closure, would see the original x. Observe: (let [x :outer f (fn [] x)

Re: Let bindings and immutability

2015-02-11 Thread gvim
On 12/02/2015 01:44, Laurens Van Houtven wrote: Hi, You’re confusing mutation with single assignment. You’re not mutating anything: 1 is still 1, 2 is still 2; you’re just assigning the same name to different numbers. The numbers themselves are immutable. It's x that bothers me, not the

Let bindings and immutability

2015-02-11 Thread gvim
Why is this possible in a language based on immutability: (let [x 1 x (inc x) x (inc x) x (inc x)] x) ;;= 4 Maybe under the hood (ie. memory registers/pointers etc.) this isn't strictly mutation but as a relative newcomer to Clojure I find it goes against the grain

Re: Let bindings and immutability

2015-02-11 Thread Laurens Van Houtven
Hi, On Feb 11, 2015, at 5:42 PM, gvim gvi...@gmail.com wrote: Why is this possible in a language based on immutability: (let [x 1 x (inc x) x (inc x) x (inc x)] x) ;;= 4 Maybe under the hood (ie. memory registers/pointers etc.) this isn't strictly

Re: Let bindings and immutability

2015-02-11 Thread James Reeves
On 12 February 2015 at 02:06, gvim gvi...@gmail.com wrote: That explains it but I think Clojure's syntax is misleading here. Without knowledge of this magic the mind doesn't readily translate: (let [x 1 x (inc x) x (inc x) x (inc x)] x) into: (let [x 1]