首页 > 解决方案 > 包含模块如何在课堂内外工作

问题描述

在 Ruby 或 Rails 中,为什么“包含”有时在类内,有时在类外?

我已经研究过上面的内容,但我无法理解的一件事是顶级include(即在类主体之外)如何将实例方法转换为类方法

例如:

module Human
  def living
    true
  end
end

include Human

现在根据上面链接问题的答案,这include使得方法Human可以从所有文件中访问(如果我错了,请纠正我)。

但是,既然定义为实例方法,为什么我可以将方法作为类方法访问呢?living

Human.living
#=> true

标签: ruby-on-railsruby

解决方案


另一个答案

任何类定义之外include Foo都会添加FooObject. [...] 的所有Foo实例方法现在随处可用。

通过在顶层包含一个模块,您实际上是在说:

Object.include(Human)

# or

class Object
  include Human
end

您缺少的是模块和类也是对象。

对象响应的方法来自其祖先,例如:

1.0.class.ancestors
#=> [Float, Numeric, Comparable, Object, Kernel, BasicObject]

'abc'.class.ancestors
#=> [String, Comparable, Object, Kernel, BasicObject]

或者,对于您的模块:

Human.class.ancestors
#=> [Module, Object, Kernel, BasicObject]

当您include Human处于顶层时,它会将该模块添加到每个对象的祖先:

include Human

1.0.class.ancestors
#=> [Float, Numeric, Comparable, Object, Human, Kernel, BasicObject]
#                                        ^^^^^

'abc'.class.ancestors
#=> [String, Comparable, Object, Human, Kernel, BasicObject]
#                                ^^^^^

Human.class.ancestors
#=> [Module, Object, Human, Kernel, BasicObject]
#                    ^^^^^

一些例子:

1.0.living   #=> true
'abc'.living #=> true
Float.living #=> true
Human.living #=> true

推荐阅读