我目前正在开发一个项目,我的代码如下所示:
# the first return is the one causing problems
def collect
return Hash["IdentANode", Array[@id, ",", @ident_a_node.collect]] unless @ident_a_node.nil? and @id.nil?
return Hash["IdentANode", @id] unless @id.nil?
end
我使用unless运算符有条件地执行return语句。出于某种原因,即使@ident_a_node
为nil
,此代码仍会执行。执行时我收到此消息:
IdentANode.rb:14:在
collect': undefined method
收集'中 nil:NilClass(NoMethodError)
这使我感到困惑,因为我曾认为,除非关键字会阻止这种情况发生。当我将语句更改为此表单时:
if not @ident_a_node.nil? and not @id.nil?
return Hash["IdentANode", Array[@id, ",", @ident_a_node.collect]]
end
或此表格:
return Hash["IdentANode", Array[@id, ",", @ident_a_node.collect]] if not @ident_a_node.nil? and not @id.nil?
返回语句是不是执行的,是什么给出的?为什么这两个陈述有区别?使用unless
关键字的多个条件会导致问题吗?
任何想法都将不胜感激
答案 0 :(得分:4)
你的逻辑失败了。您正在测试他们 nil
以避免在您应该测试时运行它 是nil
。你可能通过过多的否定层面来解决这个问题。任何不止一个都是不可接受的。
换句话说,你可以逃脱“如果它没有下雨”但不应该使用“除非is_not_raining
标志没有设置为假的倒数”之类的东西。
我个人认为,除非显而易见,否则不应使用拖尾条件。正如您在示例中所看到的,您必须水平滚动才能找到条件,隐藏开发人员的重要信息。
作为一种风格问题,当not
执行相同的工作时,请勿使用!
。其次,当你可能只想要某种定义的值时,你会专门针对nil
进行测试。
其他问题包括使用Hash[]
和Array[]
这些肯定是使用需要它们的语言的工件。与JavaScript一样,Ruby允许分别使用{ }
和[ ]
隐式声明这些内容。
适当的Ruby风格版本的代码是:
if (@ident_a_node and @id)
return { "IdentANode" => [ @id, ",", @ident_a_node.collect ] }
end
答案 1 :(得分:1)
不要使用,除非和/或,它只是简单的混淆。 unless @ident_a_node.nil? and @id.nil?
表示if !(@ident_a_node.nil? and @id.nil?)
,这意味着只要两个实例变量中的一个不是nil,它就会返回。
if !(@ident_a_node.nil? and @id.nil?)
与
相同if !@ident_a_node.nil? or !@id.nil?
哪个应该更清楚,为什么它与
不一样if not @ident_a_node.nil? and not @id.nil?