为什么不在here-doc工作中阻止参数?

时间:2013-09-01 01:08:16

标签: ruby

我试图弄清楚为什么以下代码在here-doc字符串eval中不起作用:

script = <<FILE

def i_feel(&block)
  block_given? ? "I feel #{ yield } :D" : "I don't know how I feel :/" 
end

i_feel                                  
# => "I don't know how I feel :/"

i_feel { 'great' }                   
# => "I feel great :D"
FILE

puts script

`<main>': no block given (yield) (LocalJumpError)

我知道部分原因是字符串插值。但是我如何让它发挥作用?首先尝试没有here-doc,看看它是否有效?

3 个答案:

答案 0 :(得分:7)

您可以通过使用'

包围标识符来避免在heredoc中进行插值
script = <<'FILE'
something with #{interpolation} like syntax.
FILE

puts script

这只会打印文字something with #{interpolation} like syntax.' FILE周围interpolation您可能会收到错误(如果定义了`则不会)。< / p>

你也可以使用s = <<`SCRIPT` echo foo echo bar SCRIPT (反引号)来执行heredoc的内容:

s

"foo\nbar\n"现在将包含执行heredoc的结果 - 在本例中为字符串{{1}}。

答案 1 :(得分:1)

我认为我只是想通了。

script = <<FILE

def i_feel(&block)
  block_given? ? "I feel yield :D" : "I don't know how I feel :/" 
end

i_feel                                  
# => "I don't know how I feel :/"

i_feel { 'great' }                   
# => "I feel great :D"

FILE

puts script

只需删除字符串插值括号,这里doc打印就好没有它们。我想我忘了把它设置为插值就是全部。哎呀!我会尽可能地回复你们。

也许现在我可以从中获得新的东西。至少错误消失了。 这将不再分散我的注意力。

答案 2 :(得分:0)

这是答案,更多关于我的目的是什么。你想看看你刚刚跑了什么,所以这是完整的版本。

script = <<FILE

def how_i_feel
  block_given? ? "I feel \#{ yield }." : "I don't know how I feel :/." 
end
#{ def how_i_feel
     block_given? ? "I feel #{ yield }." : "I don't know how I feel :/." 
   end }
how_i_feel
#{ how_i_feel }                                  

how_i_feel { 'great :D' }
#{ how_i_feel { 'great :D' } }    

FILE

puts script

Victor说的是对的。 这里doc也包括范围。 在这种情况下,它是插值的插值。 听起来有点混乱但只是看看这些括号的级别。 还要注意,我们必须逃避原来的#{yield},而不是尝试评估它。 这就是首先造成所有麻烦的原因。 希望这会有所帮助。

顺便说一下,这只是从https://github.com/JoshCheek/ruby-kickstart/blob/kevin_challenge/cheatsheets/blocks_procs_and_lambdas.rb

复制而来

由此您可以看到您不需要&amp; block参数。