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

4

3 回答 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
于 2009-03-03T02:51:49.413 回答
6

这是一个“here document”,它是一种内联引用大型多行字符串的方式。从编程 Ruby

字符串可以跨越多个输入行,在这种情况下,它们将包含换行符。也可以使用这里的文档来表达长字符串文字。每当 Ruby 解析序列<<identifieror<<quoted string时,它都会将其替换为从连续的逻辑输入行构建的字符串文字。当它找到以标识符或带引号的字符串开头的行时,它会停止构建字符串。您可以在字符后立即放置一个减号<<,在这种情况下,终止符可以从左边距缩进。如果使用带引号的字符串来指定终止符,则其引用规则将应用于此处的文档;否则,适用双引号规则。

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

于 2009-03-03T02:43:40.523 回答
-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
于 2009-03-03T03:49:36.683 回答