Ruby eval behaves differently in irb versus in a file

天涯浪子 提交于 2019-12-06 04:06:22

问题


This code works in irb:

irb(main):037:0> eval <<-EOS
irb(main):038:0" #{attribute} = "host"
irb(main):039:0" puts machine
irb(main):040:0" EOS
host
=> nil
irb(main):041:0> puts machine
host
=> nil
irb(main):042:0> puts attribute
machine
=> nil
irb(main):043:0>

however when I try to execute the same code as a ruby script I get the following error:

../autosys/convert_jil_to_zapp.rb:40: undefined local variable or method `machine' for main:Object (NameError)
        from ../autosys/convert_jil_to_zapp.rb:29:in `each_line'
        from ../autosys/convert_jil_to_zapp.rb:29
        from ../autosys/convert_jil_to_zapp.rb:27:in `each'
        from ../autosys/convert_jil_to_zapp.rb:27
pi929c1n10 /ms/user/h/hirscst/ruby/autosys 77$ gvim try.rb
pi929c1n10 /ms/user/h/hirscst/ruby/autosys 78$ chmod +x try.rb
pi929c1n10 /ms/user/h/hirscst/ruby/autosys 79$ ./try.rb
host
./try.rb:8: undefined local variable or method `machine' for main:Object (NameError)

can anyone explain why?


回答1:


It's because the machine variable was not already defined when eval was run. A more concise example:

Works in IRB but not as a script

eval 'x = 3'
puts x # throws an exception when run as a script
=> 3

Works in IRB and as a script

x = 1
eval 'x = 3'
puts x
=> 3

To quote Matz:

local variables should be determined at compile time, thus local variables defined first in the eval'ed string, can only be accessed from other eval'ed strings. In addition, they will be more ephemeral in Ruby2, so that these variables will not be accessed from outside.

The difference is that in IRB everything is being eval'd, so it's all in the same scope. That is, you're essentially doing this in IRB:

eval 'x = 3'
eval 'puts x'

Which works both in IRB and as a script.




回答2:


Because you're defining a method or variable named machine in IRB but not in your Ruby script.



来源:https://stackoverflow.com/questions/715010/ruby-eval-behaves-differently-in-irb-versus-in-a-file

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!