我是Ruby的新手,并将构建国际象棋作为一种学习练习。我正在尝试重构一些代码,但遇到了障碍。
为什么这样做:
@available_moves = []
#part of castling logic
@available_moves << "c1" if empty?("b1") && empty?("c1") && empty?("d1")
def empty?(position)
get_space(position).token =~ /_/
end
# sample tokens: "_e4", "ka2", "_b3"
而这不是吗?:
@available_moves = []
@available_moves << "c1" if emptyii?("b1", "c1", "d1")
def emptyii?(*positions)
positions.each { |position| get_space(position).token =~ /_/ }
end
这可能是很愚蠢的事情,但我不明白我做错了什么。
不使用each
,而是使用all?
来测试所有位置是否返回true:
positions.all? { |position| get_space(position).token =~ /_/ }
只有当块对于每个位置返回true时,positions.all?
才会为true。
就您需要做什么而言,其他答案就在这里,但您应该理解当前解决方案不起作用的原因。
你走在正确的道路上,但你只需要更深入地观察你的逻辑。让我们考虑一下代码中的两行:
@available_moves << "c1" if empty?("b1") && empty?("c1") && empty?("d1")
它说:"如果你得到b1、c1和d1的真值结果,从空返回为真,那么取c1并将其放入@available_moves中。这看起来很好,而且显然有效。
然而,看看你的另一条线:
@available_moves << "c1" if emptyii?("b1", "c1", "d1")
这意味着,"如果……那么,把c1铲到可用的_移动中,具体是什么?"如果b1是真的,但c1和d1不是,你认为emptyii是真的吗?如果所有这些都是真的,那是真的吗?到底是哪一个?
在你的第一个例子中,你有一个非常清晰的表达。然而,这不是。这就是为什么你得到了使用.all?
的建议,因为这对你想要做的事情来说要清楚得多,当然也会起作用(与你的说法相反)。