Variable scope - what is it, and how does it Ruby?
Archive - Originally posted on "The Horse's Mouth" - 2009-07-18 23:41:47 - Graham Ellis
The first whiteboard photograph with this article (Fig 1 ;-) ) shows how you define the scope of your variables in Ruby. Variables that are just bare words (i.e. don't have any special character starting them) are local to the function / method in which the name is used. That's like their family, and like referring to someone as "Bill" or "Kylie". There will be different Bills and Berts and Kylies in other families just up the road, but you just wait until Bill brings home another Kylie - the girl up the road - and you have a recipe for confusion around the dinner table. ((Does anyone still sit down for dinner??)). Variables that start with an @ character are object variables - they apply across all pieces of code that can be run on a particular object, and variables that start with two @ characters are class variables that apply to all objects of a certain type. I have another picture to show that:

You'll here terms like "instance variables", "dynamic variables" and "object variables" used too for the @ type, and "static variables" or "class variables" used for the @@ type too, depending on who you're talking to and about which programming language - moving away from Ruby, the same concept but a different syntax and varied nomenclature is used for other languages - you'll find if you come on a Perl, PHP, Python, C, Java, Lua or Tcl course that I'll still talking about scope.
The final variables that I showed in my initial diagram start with a $. They are global variables - available anywhere through the code. Now you might think it would be a good idea to make heavy use of these but emphatically it is NOT. It's all very well to use them to pass things around in smaller bits of code / scripts, but if more than a tiny proportion of your variables are scoped in this way, you make yourself a major maintainance problem as your program grows, and it becomes very hard to reuse the same code in several programs as the combining of useful bits of logic is likely to require a lot of patching of global variables on their way in and out of each piece of logic, and perhaps the dramatic updating of one or other piece of logic when you discover that both have used $result or $current.
There is an example that uses local, object and class variables here (that's the example I was writing when I put these diagrams on the board during last week's Ruby Course). Running that code you get:
Dorothy-2:pics grahamellis$ ruby d4_5
Swindon - 2 vehicles. option 1 of 4
Chippenham - 1 vehicles. option 2 of 4
Westbury - 2 vehicles. option 3 of 4
Bath - 1 vehicles. option 4 of 4
Dorothy-2:pics grahamellis$
A variety of different destinations within each object (Swindon, Chippenham, Westbury and Bath) held in a variable that starts with at @ ... and a single value for the number of pieces of public transport defined [4] in a variable that starts @@.