Skip to content

Instantly share code, notes, and snippets.

@tildedave
Created December 2, 2010 14:03
Show Gist options
  • Save tildedave/725337 to your computer and use it in GitHub Desktop.
Save tildedave/725337 to your computer and use it in GitHub Desktop.
from Andrew Kennedy
# scoping in ruby 1.8.7
x = 0
[1,2,3].each{|x| puts x}
puts x
@banister
Copy link

output is 3 in 1.8
output is 0 in 1.9

This was a bug corrected in the 1.9 branch; the 1.9 branch has now been out and stable for more than 2 years. 1.9.2 is the official ruby release.

@tildedave
Copy link
Author

Thanks for the comment! I've updated the gist to clarify that this is behavior in 1.8.7.

@ironcamel
Copy link

So ruby 1.9 is not backwards compatible? Meaning that all existing code that depended on this behavior will break in 1.9. Also, the latest version of ubuntu comes with ruby 1.8. So most people probably have ruby < 1.9, unless they build and install 1.9 themselves.

@banister
Copy link

@ironcamel, I think i already explained the situation to you in IRC?

  • This behaviour was a bug; they're allowed to fix bugs between major releases. Ruby 1.9 is to Ruby 1.8 as Python 3 is to Python 2.8; as c99 is to c89 --- all have breaking non backward compatible changes - big deal?
  • The standard way to install Ruby these days on *nix is through RVM - not through the OS package managers. Package managers are notoriously out of date for Ruby - no one uses them, and the community advises all newcomers to use RVM (for *nix) and RubyInstaller (for windows). So you're mistaken when you say people must 'build and install Ruby themselves' to get access to Ruby 1.9. Also - the Ubuntu package manager does have Ruby1.9 on it - just apt-get install ruby1.9.1-full. This is even stated on the official website: http://www.ruby-lang.org/en/downloads/
  • Hardly any code actually relied on this bug - so it hasn't been a problem shifting from 1.8 to 1.9 - so your hysteria is entirely unwarranted. Ask anyone who has made the change from 1.8 to 1.9 whether this breaking change has actually affected them, you will get a resounding 'no' as your answer.
  • However, just in case (in the 0.001% chance) your code did depend on this bug - Ruby outputs a warning in 1.9 telling you that this behaviour has changed - notably: warning: shadowing outer local variable - x

@tildedave
Copy link
Author

I definitely feel that 'weird' scoping behavior is important to know about, even if it has been fixed in later versions. Python 3 and Ruby 1.9.2 may be the most recent versions of their respective languages, but these are not the default versions on the most recent Ubuntu (for example), so there is still an awful lot of Python 2.6 and Ruby 1.8.7 code being written.

As there is no ruby specification (although https://github.com/rubyspec/rubyspec looks like an interesting project!), these implementation bugs are also bugs in the platonic Ruby language itself.

I have no political axe to grind against Ruby -- I like Ruby a lot! However, it is always interesting to me how other languages implement closures. This particular oddity is why you do a renaming on bound variables or some use mechanism like de bruijn indices in most closure implementations.

@banister
Copy link

@tildedave, I agree the scoping behaviour of 1.8.7 is important to know about; the only point i took issue with was it being labelled "Ruby Scoping Behaviour"; esp. since this behaviour has been corrected in the stable and official 1.9 branch for 2 years now. :)

Ruby is in the process of getting a specification, and there is a draft one already released, see here: http://ruby-std.netlab.jp/draft_spec/download.html

@banister
Copy link

@ironcamel,

Are you aware that Ruby 1.9 is almost a total reimplementation of Ruby? You appear to think it was a minor update.

Internally, Ruby 1.9 has very little in common with Ruby 1.8. In terms of features; Ruby 1.9 adds some major new features and cleans up a few inconsistencies and bugs - one of those bugs being the block variable scoping pointed out in this gist. Nonetheless Ruby 1.9 aims to be more or less 95% backwards compatible with Ruby 1.8 - which it has achieved.

Major releases are allowed to have breaking changes. Ruby 1.9 is a major release, it has breaking changes. In terms of 'expectation' - there were expected to be breaking changes. Once again: It is a Major Release.

Get over it. Everyone else has.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment