关于 Ruby 的一般问题

5

我在我的Rails应用程序中从github.com安装了acts_as_versioned插件,有一段代码我不太理解,希望有人能为我解决这个问题。

class_eval <<-CLASS_METHODS
  def a_bunch_of_stuff
   ....
  end
CLASS_METHODS

我知道块内的方法(或其他内容)会被定义为类内的实例方法,但我在插件中找不到常量CLASS_METHODS的定义位置,而且我也不确定class_eval后面的<<-是什么意思。该插件位于此处,相关代码位于lib/acts_as_versioned.rb的第199行。如果有人能给我解释一下这里的情况,我将不胜感激。
谢谢
-C
3个回答

7

这是一个heredoc。http://en.wikipedia.org/wiki/Heredoc#Ruby

匹配的CLASS_METHODS令牌本质上是起始和结束引号。如果您使用<<-而不是<<,则结束令牌可以缩进使用空格。

在Ruby中可以同时使用多个heredocs(我将我的heredocs设置为参数名称相同,但这只是为了美观 - 没有任何区别):

def define_with_description description, code
  puts "defining a method to #{description}"
  class_eval code
end

define_with_description <<-DESCRIPTION, <<-CODE
  set up us the bomb
DESCRIPTION
  Bomb.new.set_up(us)
CODE

6

这是一个"文档拼接表达式", 它是在一行内引用大型多行字符串的一种方式。来自《Programming Ruby》

字符串可以跨越多个输入行,此时它们将包含换行符。还可以使用文档拼接表达式来表示长字符串文字。每当Ruby解析序列 <<identifier<<quoted string 时,它将其替换为由连续逻辑输入行构建的字符串文字。当找到以标识符或引用字符串开头的行时,它停止构建字符串。您可以在 << 字符后面立即放置减号,这样终止符就可以从左边缘缩进。如果使用引用字符串来指定终止符,则其引用规则将应用于此处文档;否则,双引号规则适用。

这将导致class_evalCLASS_METHODS之间的内容视为字符串并在适当的上下文中执行。使用名称CLASS_METHODS是任意的,它也可以被称为任何其他名称。

-2

这些是等价的:

class SomeClass
  class_eval <<-CLASS_METHODS
    def first_method
    end
    def second_method
    end
  CLASS_METHODS
end

class SomeClass
  def self.first_method
  end
  def self.second_method
  end
end

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接