本文只是将有关ruby top level environment 和main Object的sample进行简单比较,仔细看完比较的结果后您自然会得结论。
运行环境是在文件中,与irb运行环境在某些地方会有出入,请参照http://www.iteye.com/topic/125046
1.top level environment 中默认receiver是一个叫main的Object
p self#main
p self.class#Object
2.默认情况,在top level environment定义的方法称为main的私有方法,在irb中貌似默认是public method。
def m
end
p self.singleton_methods(false).include? "m" #false
p Object.singleton_methods(false).include? "m" #false
p self.methods(false).include? "m" #false
p self.public_methods(false).include? "m" #false
p self.private_methods(false).include? "m"#true
p Object.instance_methods(false).include? "m" #false
p Kernel.private_methods(false).include? "m" #false
3.top level environment可以和像在普通类中一样用public声明方法定义,并且被public声明后称为所有Object实例的public method
public
def m
end
p self.singleton_methods(false).include? "m" #false
p Object.singleton_methods(false).include? "m" #false
p self.methods(false).include? "m" #false
p self.public_methods(false).include? "m" #true
p self.private_methods(false).include? "m"#false
p Object.instance_methods(false).include? "m" #true
p Kernel.private_methods(false).include? "m" #false
4.和在一般class中一样,局部变量不能被top level方法调用。
var="hooopo"
def get_var
p var
end
get_var #in `get_var': undefined local variable or method `var' for main:Object (NameError)
5.和在一般class中一样,top level定义的实例变量可以被top level中的方法调用。
@var="hooopo"
def get_var
p @var
end
get_var #"hooopo"
6.在top level定义的实例变量属于默认receiver main Object,并且不属于任何非main Object的Object。
@var="hooopo"
obj=Object.new
p obj #=>#<Object:0x2a62f64>
p self #=>#<Object:0x494f9e0 @var="hooopo">
7.top level中定义的类变量成为Object的类变量,由于类变量可以被继承到子类,并且被子类改变,才有了慎用类变量 - 实例变量靠谱量又足
中“类变量(@@xx)的问题在于它本质跟全局变量一样”的说法。。
@@var="hooopo"
def Object.get_var_in_obj
p @@var
end
class String
def String.get_var_in_str
class_variable_get("@@var")
end
def String.set_var_in_str
class_variable_set("@@var","hooopo is changed")
end
end
Object.get_var_in_obj #"hooopo"
p Object.class_variables #["@@var"]
p String.class_variables #["@@var"]
p String.get_var_in_str #"hooopo"
String.set_var_in_str
p @@var #"hooopo is changed"
8.全局变量是名副其实的全局变量,无论是在top level还是class中定义,都可以被获取。
$var="hooopo"
def get_var
p $var
end
get_var #"hooopo"
class C
$var_c="Hooopo"
def get_var
p $var_c
end
end
p $var_c #"hooopo"
c=C.new #"hooopo"
c.get_var #"Hooopo"
p $var_c #"Hooopo"
9.可以为main Object定义单体方法...
class << self
def m
p "singleton method of top-level Object instance"
end
end
m#"singleton method of top-level Object instance"
self.m #"singleton method of top-level Object instance"
o=Object.new
o.m # undefined method `m' for #<Object:0x2a62dfc> (NoMethodError)
10.main Object的单体方法调用优先于instance method。
def m
p "instance method of top level Object instance"
end
class << self
def m
p "singleton method of top-level Object instance"
end
end
m#"singleton method of top-level Object instance"
self.m #"singleton method of top-level Object instance"
11.top level环境更像是在一个类中...
def m
p "instance method of top level Object instance"
end
#class << self
# def m
# p "singleton method of top-level Object instance"
# end
#end
m#"instance method of top level Object instance"
self.m #private method `m' called for main:Object (NoMethodError)
12.public声明,让top level方法真正top level
public
def m
p "instance method of top level Object instance"
end
#class << self
# def m
# p "singleton method of top-level Object instance"
# end
#end
m#"instance method of top level Object instance"
self.m #"instance method of top level Object instance"
13.在类中可以调用top level method
def top_level_method
p "hooopo"
end
class C
def instance_method_of_c
top_level_method
end
end
c=C.new
c.instance_method_of_c #"hooopo"
13.同11
def top_level_method
p "hooopo"
end
class C
def instance_method_of_c
self.top_level_method
end
end
c=C.new
c.instance_method_of_c #`instance_method_of_c': private method `top_level_method' called for #<C:0x2a62d34> (NoMethodError)
14.优先级问题,类中实例方法优先于top level 方法
public
def top_level_method
p "hooopo"
end
class C
def top_level_method
p "hooopo-in instance method of C"
end
def instance_method_of_c
top_level_method
end
end
c=C.new
c.instance_method_of_c #"hooopo-in instance method of C"
15.优先级问题,类中实例方法优先于top level 方法,也优先于Kernel模块中方法
def puts
STDOUT.puts "from top level"
end
class C
def puts
STDOUT.puts "from insctance method of C"
end
def self.puts
STDOUT.puts "from sington method of C"
end
def call_puts
puts
end
end
c=C.new
c.call_puts #from insctance method of C
16.top level中方法优先于Kernel模块中的方法。
def puts
STDOUT.puts "from top level"
end
class C
#def puts
# STDOUT.puts "from insctance method of C"
#end
def self.puts
STDOUT.puts "from sington method of C"
end
def call_puts
puts
end
end
c=C.new
c.call_puts #from top level
17.同16
#def puts
# STDOUT.puts "from top level"
#end
class C
#def puts
# STDOUT.puts "from insctance method of C"
#end
def self.puts
STDOUT.puts "from sington method of C"
end
def call_puts
puts
end
end
c=C.new
c.call_puts #"\n"=>from Kernel?
18. 关于main Object 实现的猜测:
class Object
Object.new.instance_eval do
def self.to_s
"main"
end
private
##
# Your program gets inserted here...
##
end
end