Why the resutls are different

Hi all,

I try to understand the concept of variable scopes. I define two classes
with very similar structures. But Ruby complains class Y only. Any
comments?

Thanks,

Li

class X
  def initialize(name,artist,duration)
    @name=name
    @artist=artist
    @duration=duration
  end
  puts "This is the name"" #{name}"
end

test_x=X.new(1,2,3)
puts test_x.inspect

ruby variables1.rb

This is the name X
#<X:0x28ae894 @artist=2, @name=1, @duration=3>

Exit code: 0

class Y
  def initialize(arg1,arg2,arg3)
    @arg1=arg1
    @arg2=arg2
    @arg3=arg3
  end
   puts "This is arg1"" #{arg1}"
end

    test_y=Y.new(1,2,3)
    puts test_y.inspect

ruby variables2.rb

variables2.rb:15: undefined local variable or method `arg1' for Y:Class
(NameError)

···

Exit code: 1

--
Posted via http://www.ruby-forum.com/.

Li Chen wrote:

Hi all,

I try to understand the concept of variable scopes. I define two classes
with very similar structures. But Ruby complains class Y only. Any
comments?

Thanks,

Li

class X
  def initialize(name,artist,duration)
    @name=name
    @artist=artist
    @duration=duration
  end
  puts "This is the name"" #{name}"
end

test_x=X.new(1,2,3)
puts test_x.inspect

ruby variables1.rb
    

This is the name X
#<X:0x28ae894 @artist=2, @name=1, @duration=3>
  

Exit code: 0
    
class Y
  def initialize(arg1,arg2,arg3)
    @arg1=arg1
    @arg2=arg2
    @arg3=arg3
  end
   puts "This is arg1"" #{arg1}"
end

    test_y=Y.new(1,2,3)
    puts test_y.inspect

ruby variables2.rb
    

variables2.rb:15: undefined local variable or method `arg1' for Y:Class
(NameError)
  

Exit code: 1
    

Code in class definitions, such as your "puts" statement, is executed when the class is defined, in the context of the class being defined.
Observe that in your first example, the value of "name" that is printed is not the value of the "name" argument to initialize. It is actually the name of the class. That is because the puts statement is in the context of the class and when you print #{name} you're printing the result of calling the name method on the class object. You can simplify your example to this:

class X
   puts name
end

Check out ri Module.name.

Li Chen

I try to understand the concept of variable scopes. I define two classes
with very similar structures. But Ruby complains class Y only. Any
comments?

Thanks,

Li

class X
def initialize(name,artist,duration)
   @name=name
   @artist=artist
   @duration=duration
end
puts "This is the name"" #{name}"
end

test_x=X.new(1,2,3)
puts test_x.inspect

ruby variables1.rb

This is the name X
#<X:0x28ae894 @artist=2, @name=1, @duration=3>

Exit code: 0

class Y
def initialize(arg1,arg2,arg3)
   @arg1=arg1
   @arg2=arg2
   @arg3=arg3
end
  puts "This is arg1"" #{arg1}"
end

   test_y=Y.new(1,2,3)
   puts test_y.inspect

ruby variables2.rb

variables2.rb:15: undefined local variable or method `arg1' for Y:Class
(NameError)

Exit code: 1

In the first case, "name" is threated as "X.name" (method "name" of object
"class X").

V.

···

From: list-bounce@example.com [mailto:list-bounce@example.com] On Behalf Of
Sent: Sunday, December 17, 2006 5:17 PM

Thank you all for the quick response.

Li

···

--
Posted via http://www.ruby-forum.com/.

Also, before you get into the habit of doing that (see the quote), it's kind of considered bad form and Ruby automatically concatenating strings like that might not happen in future versions.

You can eliminate the double quotations so it is:
puts "This is the name #{name}"

Or use direct concatenation with the two strings:
puts "This is the name" + " #{name}"

But that would be silly when you can just move the space over and not have the whole #{} thing:
puts "This is the name " + #{name}

Most people, I think, would use the first version.

Dan

Timothy Hunter wrote:

···

Li Chen wrote:

  puts "This is the name"" #{name}"

Daniel Finnie wrote:

You can eliminate the double quotations so it is:
puts "This is the name #{name}"

Or use direct concatenation with the two strings:
puts "This is the name" + " #{name}"

But that would be silly when you can just move the space over and not
have the whole #{} thing:
puts "This is the name " + #{name}

Thanks,

Li

···

--
Posted via http://www.ruby-forum.com/.

Hi --

Also, before you get into the habit of doing that (see the quote), it's kind of considered bad form and Ruby automatically concatenating strings like that might not happen in future versions.

You can eliminate the double quotations so it is:
puts "This is the name #{name}"

Or use direct concatenation with the two strings:
puts "This is the name" + " #{name}"

But that would be silly when you can just move the space over and not have the whole #{} thing:
puts "This is the name " + #{name}

I think you mean:

   puts "This is the name " + name

:slight_smile: I agree that the first technique (all in one set of quotation
marks) is usually best, both because it doesn't create a new string
for the addition, and because it won't blow up if name isn't a string.
(Though maybe there are times when one would want it to, I suppose.)

David

···

On Mon, 18 Dec 2006, Daniel Finnie wrote:

--
Q. What's a good holiday present for the serious Rails developer?
A. RUBY FOR RAILS by David A. Black (http://www.manning.com/black)
    aka The Ruby book for Rails developers!
Q. Where can I get Ruby/Rails on-site training, consulting, coaching?
A. Ruby Power and Light, LLC (http://www.rubypal.com)