ruby - ruby eigen 类中的模块包含

标签 ruby class module metaprogramming

在我看来,对于instance_eval,类作用域变成了单例类,也称为目标对象的特征类。因此,在对象的单例类上创建的实例方法将成为该对象的单例方法。我的意思是以下两个代码片段产生预期结果

class TestClass; end

使用特征类

class TestClass
  class << self   
    def class_method
      "class_method of TestClass"
    end
  end
end

使用instance_eval

TestClass.instance_eval do
 def class_method2
   "class_method of TestClass"
 end
end

这样我们就可以调用TestClass.class_method和TestClass.class_method2并得到相应的结果。 现在假设我们有一个模块 TestModule

module TestModule
  def instance_method
    " instance_method from TestModule"
  end
end

现在,如果我们将此模块包含在 eigen 类中,那么我们可以将instance_method 作为 TestClass 的类方法进行访问

class TestClass
  class << self   
    include TestModule
  end
end

因此 TestClass.instance_method 将按预期工作。

但是如果我们使用instance_eval做同样的事情,它就会失败。请检查以下代码片段

TestClass.instance_eval do
  include TestModule
end

当我尝试调用 TestClass.instance_method 时,出现以下错误。

ArgumentError: wrong number of arguments(0 for 1)

有人能解释一下问题是什么以及其背后的内部逻辑是什么吗?我非常感谢您提供的任何帮助。

最佳答案

这是因为如果你使用include当前类是什么并不重要,重要的是self指向什么(include 是在 self 上调用的方法(如果您没有指定显式接收者),在您的示例中,self 指向 TestClass,因此 TestModule#instance_method 成为 TestClass 的实例方法,如下例所示:

class TestClass
end

module TestModule
  def test_method
    'test'
  end
end
TestClass.instance_eval { include TestModule }
TestClass.new.test_method
# => "test"

关于ruby - ruby eigen 类中的模块包含,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27438542/

相关文章:

c++ - 如何在类,c++中使用带参数的函数?

angular - 组件是两个模块 :AppRoutingModule and AppModule 声明的一部分

java - 如何在android中创建带标题的水平图片列表?

ruby-on-rails - 名称错误 : uninitialized constant on Heroku

c# - 为什么泛型 class<T> 中的 List<T>.RemoveAll 需要 Predicate 的变体形式?

javascript - Ruby - 如何提取字符串中的 £ 符号以进行浮点转换

python - 使用 Luigi 管道时组织文件?

linux - 在内核模块中创建以太网数据包并发送

ruby - Middleman 3.0 - 简单导航 gem

ruby - 如何创建一个方法来检查字符串是否以大写字母开头?