如何拯救 Ruby 中的 eval?

Posted

技术标签:

【中文标题】如何拯救 Ruby 中的 eval?【英文标题】:How to rescue an eval in Ruby? 【发布时间】:2010-10-07 06:28:37 【问题描述】:

我正在尝试解决在 Ruby 1.8.6 中eval()ing 代码时出现的语法错误。

我希望得到以下 Ruby 代码:

#!/usr/bin/ruby

good_str = "(1+1)"
bad_str = "(1+1"    # syntax error: missing closing paren

begin
    puts eval(good_str)
    puts eval(bad_str)
rescue => exc
    puts "RESCUED!"
end

运行时产生以下结果:

2
RESCUED!

相反,我得到的是:

2
eval_rescue.rb:8: (eval):1: compile error (SyntaxError)
(eval):1: syntax error, unexpected $end, expecting ')'

看来 eval 方法引发的 SyntaxError 正在 eval 中的某个地方被救出,而我没有机会自己处理它。

有人知道如何获得我想要的行为(即,让我的“救援”子句从“评估”中捕获错误)吗?

【问题讨论】:

【参考方案1】:

Brent 已经获得了answer that works,但我建议您从可以逃脱的最小异常集中解救出来。这样可以确保您不会意外吞食一些您不想成为的东西。

因此,

begin
  puts eval(good_str)
  puts eval(bad_str)
rescue SyntaxError => se
  puts 'RESCUED!'
end

【讨论】:

这是个好建议。例如,拯救 Exception 而不是 SyntaxError 将防止您使用 ctrl-C 中断您的进程。 我很惊讶这并没有成为最佳实践。【参考方案2】:

嗯,这很容易......

事实证明,默认情况下,“rescue”语句不会捕获所有异常,而只会捕获 StandardError 的子类。 SyntaxError 是 StandardError 的兄弟/表亲,而不是它的子类,因此除非明确告知,否则救援语句不会捕获它。

要让救援块捕获所有异常,您需要将代码更改为以下内容:

#!/usr/bin/ruby

good_str = "(1+1)"
bad_str = "(1+1"    # syntax error: missing closing paren

begin
    puts eval(good_str)
    puts eval(bad_str)
rescue Exception => exc
    puts "RESCUED!"
end

注意“rescue”行的变化,从“rescue => exc”到“rescue Exception => exc”。

现在,当您运行代码时,您会得到想要的结果:

2
RESCUED!

【讨论】:

请看这个:***.com/questions/10048173/…

以上是关于如何拯救 Ruby 中的 eval?的主要内容,如果未能解决你的问题,请参考以下文章

Ruby | 家装新思路,垂直式设计拯救你的一成不变

如何从子进程中的致命错误中拯救父进程

C++-拯救行动 解题思路

拯救者可以用小新pad当副屏吗

拯救行动(BFS)

病毒来了,如何拯救企业信息安全