From: "Hal E. Fulton" Date: 2001-06-01T14:51:25+09:00 Subject: [ruby-talk:16118] Re: Strange idea... exporting from a scope ----- Original Message ----- From: Wayne Blair To: ruby-talk ML Sent: Thursday, May 31, 2001 10:18 PM Subject: [ruby-talk:16114] Re: Strange idea... exporting from a scope > Hi Hal, > > Maybe I'm missing something (like I have no idea what the block problem is), > but why wouldn't you just declare the variable in the outer scope then set > it from inside the block: > > my_var = nil > my_method do |x,y,z| > # ... > my_var = 123 > #... > end > puts my_var # 123 Hi Wayne... I always get confused by this, and I'm a fool for answering this email at nearly 1 a.m. my time... my neurons are firing very sluggishly. Here is my summary of the block problem. (I'm likely missing some points.) 1. Intuition (for many people) says that the entities in the "parameter" list (which really isn't a parameter list, right?) are local to the block. 2. Their intuition is wrong. If Ruby sees a variable in the list that already exists, it will use the existing one. 3. Some people at some times hate this. They don't want a variable trounced just because they used a variable of the same name in an innocent-looking context. They would like to see these variables all become block-local by default. 4. Other people at other times would hate the default-block-local behavior. They depend on the existing behavior so as not to have to create unnecessary variables and do extraneous assignments. item = nil x.each do |item| if condition(item) break end end puts item # This one caused the failure # item = nil above is needed, or item is unknown here 5. I still favor the symbol idea -- if a param is a symbol, then it refers to the outer scope; if not, it's block-local. This will still break old code, but I think it is more intuitive than the reverse (which would not break old code). And if it's a symbol, and the variable doesn't exist yet, then create it. x = 5 # and y doesn't exist my_meth do | x, :y | x = 6 y = 7 end puts x # 5 (unchanged) puts y # 7 (new var) Not *all* code would be broken anyhow... only that which depended on this feature. If you're not doing an "implicit import and export" of a variable, you're in good shape. 6. I suppose the only thing that the export method would save you is having to define a variable before the block. That reminds me too much of a variable declaration in this case (and Ruby does not have those, as such). The reason is that we expect "the stuff the block does" to be understandable from reading the block. But its behavior is radically changed by something *before* the block. (Yes, I know that all locals are available inside the block -- that's not my point -- the point is that I just forgot the point.) Anyway, I guess #5 above is still my favorite solution... but I was intrigued by the idea of a variable being "exported" from a scope. Thanks for replying, Hal