This situation calls for a CSV custom converter.
Write the CSV file
Let's first create a CSV file from the following information.
FName = 't.csv'
headers = ["company", "vals", "phone_nbrs"]
rows = [
['ABC', [1.3, 2.1, 4.1], ["800-555-1000", "800-555-1001"]],
['XYZ', [7.3, 9.5], ["800-555-2000", "800-555-2001"]]
]
I will do that by converting each of the arrays in rows to a string containing elements of the array converted to strings and separated by a space. For example, [1.3, 2.1, 4.1] will be saved as the string:
[1.3, 2.1, 4.1].join(' ')
#=> "1.3 2.1 4.1"
As will be seen, this particular string representation of arrays is arbitrary, just one among many ways of doing that. For example we could save the array of floats shown above as "1.3:2.1:4.1" or "1.3¯\\_(ツ)_/¯2.1¯\\_(ツ)_/¯4.1".
Let's now create the CSV file.
require 'csv'
CSV.open(FName, "w") do |csv|
csv << headers
rows.each { |name,vals,phone_nbrs|
csv << [name, vals.join(' '), phone_nbrs.join(' ')] }
end
Let's see what was written.
puts File.read(FName)
company,vals,phone_nbrs
ABC,1.3 2.1 4.1,800-555-1000 800-555-1001
XYZ,7.3 9.5,800-555-2000 800-555-2001
Read the CSV file
The trick here is to define a converter that converts the strings of strings representing floats to arrays of floats and the strings of telephone numbers to arrays of strings.
convert_arrays = lambda do |value, field|
case field.header
when 'vals'
value.split.map(&:to_f)
when 'phone_nbrs'
value.split
else
value
end
end
#=> #<Proc:0x0000599427913ec0@(irb):19 (lambda)>
Now read the file into an array.
CSV.foreach(FName, :headers => true, converters: [convert_arrays]).
with_object([]) { |row, arr|
arr << row.values_at('company', 'vals', 'phone_nbrs') }
#=> [["ABC", [1.3, 2.1, 4.1], ["800-555-1000", "800-555-1001"]],
# ["XYZ", [7.3, 9.5], ["800-555-2000", "800-555-2001"]]]
See CSV::new and these examples of CSV converters.
tadmanpointed out you might be better off using json or yaml, if you want to store and read complex data from a text-representation. Both formats would support Arrays, while in csv - as the current awnser explains - requires you to choose a custom serialization for you values. Then again, when reading from your csv file, you need the knowledge of how exactly you serialized the array to be able to deserialize it. For json / yaml you can rely on existing parsers to do the job right.