我已经通过打印验证了方法中的index不是nil。我还做了index == nil 仔细检查。
我在这里错过了什么?
不是index 是nil,而是new_array。错误消息说:
undefined method `<<' for nil:NilClass
并且指的是new_array << index这一行。这里,<< 是方法,new_array 是接收器。由于某种原因,new_array 是 nil。
你可能认为new_array 是[],因为你明确地说了new_array = []。但是方法有自己的局部变量范围。如果你在方法之外定义了一个局部变量,它在方法内部将不可用,反之亦然。
通常当引用一个未定义的变量时,你会得到:
undefined local variable or method `new_array'
但在这里,第二个作业隐藏了实际问题:
new_array = array.each do |index|
^^^^^^^^^^^
当 Ruby 遇到这一行时,它会立即创建一个初始值为 nil 的局部变量 new_array。 (局部变量是在解析行时创建的,而不是在赋值时创建的)
要获得预期的结果,您必须将new_array = [] 移入方法,摆脱new_array = array.each { ...} 的赋值并在最后返回new_array:
def substrings(word, array)
new_array = []
array.each do |index|
if index.include?(word)
new_array << index
end
end
new_array
end
变量名称有点随意,甚至可能会产生误导。拥有index.include?(word) 看起来您正在将数字索引与字符串进行比较。我会使用这样的东西:
def substrings(substring, words)
result = []
words.each do |word|
if word.include?(substring)
result << word
end
end
result
end
在代码方面,您可以通过 each_with_object 将数组合并到循环中,这也将返回数组:
def substrings(substring, words)
words.each_with_object([]) do |word, result|
if word.include?(substring)
result << word
end
end
end
但是,根据条件选择元素是一项非常常见的任务,Ruby 提供了一个专用方法 select - 您只需从块中返回 true 或 false 以指示是否应选择元素:
def substrings(substring, words)
words.select do |word|
word.include?(substring)
end
end