6

我想用 irb 和我试图 gsub 的 HTML 页面做一些正则表达式测试。

然而,我们都知道和喜爱的 HEREDOC 语法在 Ruby 中似乎有所不同:

irb(main):140:0> text = <<-FUNUNU <p class="firstpara">
irb(main):141:0" FUNUNU
irb(main):142:0*
irb(main):143:0* puts text
SyntaxError: compile error
(irb):140: syntax error, unexpected kCLASS, expecting kDO or '{' or '('
text = <<-FUNUNU <p class="firstpara">
                         ^
(irb):143: syntax error, unexpected tIDENTIFIER, expecting kDO or '{' or '('
        from (irb):143
        from :0

它似乎在抱怨字符串的内容,试图解释它。从我能找到的关于 HEREDOC 语法的所有文档中,都指出关键字之间的所有内容都应该是变量的一部分。但似乎并非如此。

除了 HEREDOC 字符串以 HEREDOC 指标的第二个表达式结尾之外,字符串的内容是否存在格式限制?

4

3 回答 3

15

你不能把字符串放在heredoc分隔符的同一行,因为在分隔符之后,在同一行,允许放置Ruby代码,即

irb> text = <<-FOO # Ruby code allowed here...
irb*   <a class="foo">
irb* FOO
# => "<a class=\"foo\">\n" 
irb> text
# => "<a class=\"foo\">\n"

这是因为你可以这样写:

irb> instance_eval(<<-CODE)
irb* def foo
irb*   "foo"
irb* end
irb* CODE

甚至:

def foo(a, b, c)
  [a, b, c]
end

foo(<<-A, <<-B, <<-C)
foo
A
bar
B
baz
C
# => ["foo\n", "bar\n", "baz\n"]
于 2013-06-13T13:36:34.917 回答
6

As has been pointed out, the heredoc text begins on the next line after the heredoc terminator. This is not meant to replace those answers but rather provide a possibly better alternative to the typical heredoc syntax.

I personally prefer to use %q{}. It equates to using single quotes. The following give the same output:

text = %q{ <a class="foo"> }
text = ' <a class="foo"> '

If you would like to use string interpolation:

text = %Q{ <a class="#{class_name}">}

You can also switch out the {} for other terminators. The following two lines give exactly the same output:

text = %Q[ <a class="#{class_name}">] 
text = %Q| <a class="#{class_name}">|

And they support multiple lines:

text = %q{<p>
Some text
</p>}

There are some good answers on this SO question in reference to different uses for this syntax.

于 2013-06-13T13:47:36.287 回答
2

heredoc 的第一行允许额外的 ruby​​。字符串在回车后开始。

http://ruby-doc.org/docs/ruby-doc-bundle/Manual/man-1.4/syntax.html#here_doc

于 2013-06-13T13:34:37.160 回答