我最近看到了两种在Ruby中使用结构创建类的方法:
Customer = Struct.new(:name, :address) do
# ...
end
class Customer < Struct.new(:name, :address)
# ...
end
这些方法之间有什么区别?
答案 0 :(得分:4)
Ruby实际上有几个范围:
# scope one, opened with `module` keyword
module ...
# scope two, opened with `class` keyword
class ...
end
end
module
,class
其中一些。
当您使用第一个示例时,您可以共享范围以访问f
变量,在某些情况下它非常方便:
=> f = 1
=> 1
=> Customer = Struct.new(:a) do
=> puts f
=> end
=> 1
=> #<Customer:0x005561498351f8>
使用第二个示例,您无法访问f
变量变量:
=> f = 1
=> class Customer < Struct.new(:a)
=> puts f
=> end
#> NameError: undefined local variable or method `f' for Customer:Class
祖先链也有区别 - 请参阅@ AndreyDeineko的回答。
答案 1 :(得分:4)
一些区别在于祖先链。
第一个例子:
Customer.ancestors
#=> [Customer, Struct, Enumerable, Object, PP::ObjectMixin, Kernel, BasicObject]
第二个例子:
Customer.ancestors
#=> [Customer, #<Class:0x007ff4328dddc0>, Struct, Enumerable, Object, PP::ObjectMixin, Kernel, BasicObject]
因此,在第一个例子中,Customer
的超类本身就是一个Struct
类,而在第二个例子中,它是一个匿名类#<Class:0x007ff4328dddc0>
。
两个Customer
如何访问其定义范围的变量也有所不同 - 请参阅@Зеленый的答案。