Ruby 只需一行程序就可以执行一条语句

Ruby 只需一行程序就可以执行一条语句,ruby,debugging,Ruby,Debugging,我正在寻找最短、最简单的Ruby one liner,以便只执行一次语句。这个想法是在调试时使用它来快速地将调试语句添加到一个只执行一次的循环中 到目前为止,我想到的最好的方法是: puts "do something interesting exactly once!" if (once ||= "0").next! == "1" 你能想出更短的吗 补充澄清: 这些问题的想法是把重点放在“一次性”部分,而不是“做一些有趣的事情”部分。应该假设代码执行一次可以是任何东西,而不仅仅是puts语句

我正在寻找最短、最简单的Ruby one liner,以便只执行一次语句。这个想法是在调试时使用它来快速地将调试语句添加到一个只执行一次的循环中

到目前为止,我想到的最好的方法是:

puts "do something interesting exactly once!" if (once ||= "0").next! == "1"
你能想出更短的吗

补充澄清:

这些问题的想法是把重点放在“一次性”部分,而不是“做一些有趣的事情”部分。应该假设代码执行一次可以是任何东西,而不仅仅是puts语句

理想的解决方案也适用于不同类型的循环构造。例如,正如所指出的,我最初的解决方案只有在循环上下文之外已经定义了
once
变量,或者所使用的循环上下文没有创建新的词汇范围时才有效

引发这个问题的最初用例略有不同——它看起来更像下面的例子。但我认为上面这个简单的例子更容易解释我所寻找的解决方案

def process
  do_some_preprocessing()

  raise SomeError if <once> # added temp. for debugging purposes - the <once> part is what this question is about!
  dangerous_operation() # this can raise SomeError under certain conditions

rescue SomeError
  attempt_to_rescue() and retry
end
def过程
做一些预处理()
如果#添加了温度,则引发一些错误。为了调试的目的-这部分就是这个问题的内容!
危险的_操作()#在某些情况下,这可能会引起一些错误
挽救一些错误
尝试\u拯救(),然后重试
结束

最初的想法会产生代码气味。这会导致代码让其他人挠头,这不是一件好事。生成清晰易懂的代码将使您和其他程序员的工作更轻松

如果您正在调试,那么编写需要一段时间才能理解的代码将需要一段时间才能理解,所以请善待您未来的自己

我会坚持标准方式,使用一个简单的标志:

once = false
2.times do
  puts "do something interesting exactly once!" unless once
  once ||= true
end
这将导致此输出:

# >> do something interesting exactly once!

嗯,你可以滥用lambdas和闭包

->{puts "do something interesting exactly once!";x=->{x}}[][]
#=> do something interesting exactly once!
#=> #<Proc:0x5465282c@(irb):10 (lambda)>
(编辑答案以反映评论中的讨论)

您的代码不会执行您希望它执行的操作,它将取决于您使用的循环构造

这将有助于:

puts "do something interesting exactly once!" if once = once.nil?
但是有了这个,您必须在之前定义
one
one=nil
(对于您自己的代码也是如此)。这是因为,否则,
once
变量的范围将限制在
每个
循环内的块中,从而导致它失败。这在
for循环
中可以正常工作(您必须以测试它的方式):

为了避免该问题而不必首先初始化变量,您可以将
设置为一次
全局:

(1..3).each do
  puts "$once's scope is not restrained to the 'each' loop! Works!" if $once = $once.nil?
end
# >$once's scope is not restrained to the 'each' loop! Works!

顺便说一句,你当前的代码不像你说的那样,是吗?我只想到一个词:为什么?您不希望代码可读吗?这只是一个挑战吗?(如果是这样的话,这是离题的,有一个不同的SE)我会继续玩:
put one=“只做一次有趣的事情!”除非有一次
.Patrice(以及其他指出这一点的人)-是的,它可以工作,但取决于它所使用的循环构造的类型。对于其他类型的上下文,可以使用实例变量,例如,
@once
而不是'once.Arran-不,目标不是可读性最高的代码,而是需要最少键入的代码。正如我所说的(可能还不够清楚),这个想法只是为了调试而临时添加这个代码。完成后,我将再次从代码中删除它。就像您将任何其他打印语句临时添加到代码中以进行调试,以找出某个变量的值一样-除了在这种情况下我只想打印一次。更好地工作不是问题。字符串永远不会打印,
(once | |=true)
总是返回true。我的意思是,那些“解决方案”一开始就不符合他的要求。我现在不能测试它,但我很确定…@Ali是的,这个不会显示任何东西,OP的一个每次都会显示。
(once | |=true)总是返回true
。是的。哦,好吧。不管怎么说,做OP想要做的事情是个坏主意。+1因为我从来没有想过一个自我修改的lambda,这可能会很有用。(你应该显示它打印一次)不起作用。尝试:
5.times do x=->{puts“只做一次有趣的事情!”;x=->{}x.call end
你的答案与尝试类似:
x=true;如果x,则放“hello”;x=假@7stud是的,但他会在循环之外定义lambda。然后
在循环中调用它。@particie Gahide,那为什么还要麻烦lambda呢?您可以只写
x=true;5.times{如果x;x=false,则输入“hi”}
`+1 x将在打印一次后执行武士seppuku(杀死它自己):)如果您不在之前定义
一次
,则
一次.nil?
将失败。我想。无法测试。不,不会的!如果之前设置了
one=nil
,它可以像您预期的那样打印一次。如果您不介意,我可以使用一些测试代码进行编辑如果
one
未定义,
one=one.nil?=>true
(即使
once.nil?=>未定义);接下来,
true=once.nil=>false
(无打印)。此后
false=one.nil=>false
(无打印)。哈!@尼米尔,别拘束。@Nirim,我的互联网丢了一段时间了
one=one.nil=>true
one=tweep.nil?
引发了一个“未定义的局部变量或方法”异常,因此我假设在第一种情况下,Ruby在创建变量
one
后执行右侧,该变量最初的值为
nil
。有道理?我不明白为什么
for
的行为不同,但它似乎与范围有关
for
模拟执行
“只做一次有趣的事情!”如果once=one.nil?
连续三次,这就是我最初测试的方式。
(1..3).each do    # 3.times would behave just the same
  puts "once has not been defined before! Won't work!" if once = once.nil?
end
# >once has not been defined before! Won't work!
# once has not been defined before! Won't work!
# once has not been defined before! Won't work!

for i in 1..3 do
  puts "Works because of the way for loops treat vars within loop" if once = once.nil?
end
# >Works because of the way for loops treat vars within loop
(1..3).each do
  puts "$once's scope is not restrained to the 'each' loop! Works!" if $once = $once.nil?
end
# >$once's scope is not restrained to the 'each' loop! Works!
debug = ["do something interesting exactly once!"]
puts debug.pop # "do something interesting exactly once!"
puts debug.pop # nil