我有代码检查CSV文件是否正确。我想编写惯用的代码来检查列是否正确。如果我们有第一行检查列,我不想写块检查。
CSV.foreach(@csv) { |person|
first_name, last_name, person_id, email, title, phone, mobile, department, address, city = person[0..9]
zip_code, state, country, manager_id =person[10..13]
@managers << manager_id
@persons << person_id
validate = false unless validate_email(email)
validate = false unless validate_first_name(first_name)
validate = false unless validate_last_name(last_name)
validate = false unless validate_person_id(person_id)
}
答案 0 :(得分:1)
CSV是否有标题或是否可以添加标题?如果是,您可以执行CSV.foreach(@csv, :headers => true)
并获取类似person['first_name']
的列值。然后最后的检查变为
validate = false unless validate_email(person['email'])
那就是说,似乎你最后的整个验证都可以写成
validate_email(person['email']) && validate_first_name(person['first_name']) etc.
答案 1 :(得分:0)
+1迈克尔对:headers => true
但是如果你想验证你的例子中的所有命名字段并且是为了DRY(尽管如此,可能有点过于聪明的可维护性),你可以使用Enumerable#inject:
CSV.foreach(@cvs, :headers => true) { |person|
@managers << person[:manager_id]
@persons << person[:person_id]
# Array of columns to be validated
validate_cols = [:first_name, :last_name, :person_id, :email, :title, :phone,
:mobile, :department, :address, :city, :zip_code, :state,
:country, :manager_id]
valid = validate_cols.inject(true){|valid_sum, col|
valid_sum && send("validate_#{col}", person[col])
}
}
这假设您为validate_*
数组中命名的每个列都有validate_cols
个方法。