From: hipster Date: 2000-12-01T17:46:10+09:00 Subject: [ruby-talk:6697] Re: each/for binding confusion and resolution On Fri, 01 Dec 2000 03:10:02 +0900, Steven Grady wrote: > hipster responds: > >Would, a construct similar to Thread.new, > > > > proc([arg*]) { |args| block } -> aProc > > > >reduce the surprise? (I may overlook some binding semantics here, just > >an idea) > > Interesting. In the Hacker's Dictionary interpretation, I presume? :) > I'm not sure if you meant that the "arg*" list would be passed on > as the block's "args" list. If so, there's a problem, because blocks > already take a set of arguments. An alternative interpretation is simply > that the arguments of proc() are to be used locally (i.e. the block > gets their value, not the variable itself). The alternative, that's exactly what I meant. > One of my original questions was whether you could achieve > my intent using a loop instead of an iterator. > Using the above syntax (with my alternative semantics), it would > be something like: > procs = [] > for v in [1, 2] > procs << proc(v) { v } > end > > By putting the "v" in the argument list of proc(), I am indicating that > the v should be derefenced now, rather than when the Proc is called. Leaving the |'s out is an even better idea. Instead of dereferencing, I think a reference to v.clone should be stored in the proc's binding instead of v itself. > This would also address the scoping problem. So even if v had been > previously defined, you could still do this with : > v = nil # Note that this prevents v from being block-local > procs = [] > [1, 2].each {|v| > procs << proc(v) { v } > } > > Unfortunately, I'm guessing there is no way to reimplement such a change > within Ruby; Proc.new would have to be changed inside the interpreter. > (Perhaps it could be done in Ruby if the Binding class had instance methods > to modify the bindings, but that's a mere dream..) The vector [scoping rules, notation, backward compatibility] has been challenged before... Maybe something for Ruby 1.8? Michel