此代码有什么问题?
我有一个.txt文件,其中包含一些这样的属性:
attr_one, att2, attr3, attr4
attr_one, att2, attr3, attr4
attr_one, att2, attr3, attr4
我想将“ attr1”更改为“ attr_one”
require "csv"
people = CSV.read("text.txt")
attr_one = people.find { |person| person[0] =~ /attr_one/ }
attr_one[0] = "attr_one_new"
CSV.open("text.txt", "w") do |csv|
people.each do |person|
csv << person
end
end
以及如何更改它以启动前面的代码?
attr_one[0]...
这是一本参考手册中的示例。
此代码的输出应为如下数组:
attr_one, att2, attr3, attr4
attr_one_new, att2, attr3, attr4
attr_one, att2, attr3, attr4
哪里有错?
答案 0 :(得分:0)
问题在于find
返回nil
,因为该块从不返回真实值。
attr_one = people.find { |person| person[0] =~ /attr_one/ }
这将导致调用以下行。
attr_one[0] = "attr_one_new"
因为nil
没有[]=
的设置器。
这里的收获是find
可以返回nil
值。
find(ifnone = nil){| obj |块}→obj或nil
查找(ifnone = nil)→an_enumerator
将枚举中的每个条目传递给 block 。返回第一个 block 不是假的。如果没有对象匹配,则调用 ifnone 并返回其 指定时返回结果,否则返回
nil
。如果没有给出块,则返回一个枚举数。
(1..100).detect #=> #<Enumerator: 1..100:detect> (1..100).find #=> #<Enumerator: 1..100:find> (1..10).detect { |i| i % 5 == 0 and i % 7 == 0 } #=> nil (1..10).find { |i| i % 5 == 0 and i % 7 == 0 } #=> nil (1..100).detect { |i| i % 5 == 0 and i % 7 == 0 } #=> 35 (1..100).find { |i| i % 5 == 0 and i % 7 == 0 } #=> 35