রুবিতে সিএসভিতে আউটপুট অ্যারে


185

রুবির সাথে একটি অ্যারেতে কোনও CSV ফাইলটি পড়া খুব সহজ তবে আমি কোনও CSV ফাইলে অ্যারে কীভাবে লিখব সে সম্পর্কে কোনও ভাল ডকুমেন্টেশন খুঁজে পাই না। কেউ আমাকে কীভাবে বলতে পারেন?

আমি রুবি ব্যবহার করছি 1.9.2 যদি এটি গুরুত্বপূর্ণ।


3
আপনার কাছে উত্তরটি দুর্দান্ত, তবে আমাকে আপনাকে সিএসভি ব্যবহার না করার জন্য অনুরোধ করুন। আপনার যদি আপনার ডেটাতে ট্যাব না থাকে তবে ট্যাব-বিস্মৃত ফাইলগুলি মোকাবেলা করা আরও সহজ কারণ এগুলিতে এতগুলি ফ্রায়াকিনের উদ্ধৃতি এবং পলায়ন এবং এগুলি জড়িত না। আপনার অবশ্যই সিএসভি ব্যবহার করা উচিত, অবশ্যই তাদের বিরতি।
বিল দাবার

8
@ বিল, সিএসভি মডিউল ঝরঝরে ট্যাব-সীমিত ফাইলগুলি পাশাপাশি আসল সিএসভি ফাইলগুলি পরিচালনা করে। : Col_sep বিকল্পটি আপনাকে কলাম বিভাজককে "\ t" হিসাবে নির্দিষ্ট করতে দেয় এবং সমস্ত কিছু ঠিক আছে।
tamouse


এই মডিউলটি দিয়ে .tab ফাইলগুলি ব্যবহার করা আমি যা করছি তা হ'ল, কারণ দুর্ঘটনাক্রমে এক্সেলের মধ্যে এটি খোলার ফলে এনকোডিং খারাপ হয়ে যাবে ...
MrVocabulary

উত্তর:


326

একটি ফাইলের কাছে:

require 'csv'
CSV.open("myfile.csv", "w") do |csv|
  csv << ["row", "of", "CSV", "data"]
  csv << ["another", "row"]
  # ...
end

একটি স্ট্রিং:

require 'csv'
csv_string = CSV.generate do |csv|
  csv << ["row", "of", "CSV", "data"]
  csv << ["another", "row"]
  # ...
end

এখানে সিএসভি-তে বর্তমান ডকুমেন্টেশন: http://ruby-doc.org/stdlib/libdoc/csv/rdoc/index.html


1
@ ডেভিড এটি ফাইল মোড। "ডাব্লু" অর্থ একটি ফাইলে লিখুন। আপনি যদি এটি নির্দিষ্ট না করেন তবে এটি "আরবি" (কেবলমাত্র পঠনযোগ্য বাইনারি মোড) এ ডিফল্ট হয়ে যাবে এবং আপনার সিএসভি ফাইলটিতে যুক্ত করার চেষ্টা করার সময় আপনি একটি ত্রুটি পাবেন। রুবিতে বৈধ ফাইল মোডের তালিকার জন্য রুবি- doc.org/core-1.9.3/IO.html দেখুন ।
ডিলান মার্কো

15
Gotcha। এবং ভবিষ্যতের ব্যবহারকারীদের জন্য, আপনি যদি প্রতিটি পুনরুক্তিটি পূর্ববর্তী সিএসভি ফাইলটি ওভাররাইট না করতে চান তবে "ab" বিকল্পটি ব্যবহার করুন।
বোল্ডার_রবি

1
রুবি ফাইল আইও মোডগুলির
নিক

37

আমি এটিকে এক লাইনে নামিয়েছি।

rows = [['a1', 'a2', 'a3'],['b1', 'b2', 'b3', 'b4'], ['c1', 'c2', 'c3'], ... ]
csv_str = rows.inject([]) { |csv, row|  csv << CSV.generate_line(row) }.join("")
#=> "a1,a2,a3\nb1,b2,b3\nc1,c2,c3\n" 

উপরের সমস্ত কিছু করুন এবং একটি লাইনে একটি সিএসভিতে সংরক্ষণ করুন।

File.open("ss.csv", "w") {|f| f.write(rows.inject([]) { |csv, row|  csv << CSV.generate_line(row) }.join(""))}

বিঃদ্রঃ:

একটি সক্রিয় রেকর্ড ডাটাবেসকে সিএসভিতে রূপান্তর করা এমন কিছু আমার মনে হয়

CSV.open(fn, 'w') do |csv|
  csv << Model.column_names
  Model.where(query).each do |m|
    csv << m.attributes.values
  end
end

হুম @ টমাউস, সেই কথাটি সিএসভি উত্স না পড়ে আমার কাছে কিছুটা বিভ্রান্ত করছে, তবে সাধারণভাবে, ধরে নিচ্ছি আপনার অ্যারেতে প্রতিটি হ্যাশ একই সংখ্যক কে / ভি জোড় রয়েছে এবং কীগুলি সর্বদা একই, একই ক্রমে (যেমন) যদি আপনার ডেটা কাঠামোগত হয়) তবে এটি করা উচিত:

rowid = 0
CSV.open(fn, 'w') do |csv|
  hsh_ary.each do |hsh|
    rowid += 1
    if rowid == 1
      csv << hsh.keys# adding header row (column labels)
    else
      csv << hsh.values
    end# of if/else inside hsh
  end# of hsh's (rows)
end# of csv open

যদি আপনার ডেটা কাঠামোগত না হয় তবে এটি অবশ্যই কাজ করবে না won't


আমি CSV.table ব্যবহার করে একটি সিএসভি ফাইল টেনেছি, কিছু হেরফের করেছি, কিছু কলাম থেকে মুক্তি পেয়েছি এবং এখন আমি ফলাফলের অ্যারেটিকে আবার সিএসভি হিসাবে আউট করতে চাই (সত্যিই ট্যাব-বিসীমাবদ্ধ)। কিভাবে? gist.github.com/4647196
tamouse

হুম ... যে গিস্টটি কিছুটা অস্বচ্ছ, তবে একই
ক্রশে

ধন্যবাদ, @ বোল্ডার_ রবি। এটা চলবে. তথ্যটি একটি শুমারি সারণি, এবং সেই সূচনাটি বরং এটির দিকে ফিরে তাকানো অস্বচ্ছ। :) এটি মূলত একটি উপসেটে মূল শুমারির সারণী থেকে নির্দিষ্ট কলামগুলি বের করছে।
tamouse

3
আপনি injectএখানে অপব্যবহার করছেন , আপনি সত্যিই ব্যবহার করতে চান map। এছাড়াও, আপনাকে joinডিফল্ট হিসাবে খালি স্ট্রিংটি পাস করার দরকার নেই । সুতরাং আপনি এটিকে আরও সঙ্কুচিত করতে পারেন:rows.map(&CSV.method(:generate_line).join
আইগেল

1
আপনার দ্বিতীয় উদাহরণটি অত্যধিক জটিল, কারণ সিএসভি লাইব্রেরি বেশ শক্তিশালী। CSV.generate(headers: hsh.first&.keys) { |csv| hsh.each { |e| csv << e } }সমতুল্য সিএসভি উত্পন্ন করে।
আমদান

28

আপনার যদি ডেটার অ্যারেগুলির একটি অ্যারে থাকে:

rows = [["a1", "a2", "a3"],["b1", "b2", "b3", "b4"], ["c1", "c2", "c3"]]

তারপরে আপনি নীচের সাথে কোনও ফাইলে এটি লিখতে পারেন, যা আমি মনে করি এটি অনেক সহজ:

require "csv"
File.write("ss.csv", rows.map(&:to_csv).join)

20

যদি কেউ আগ্রহী হন তবে এখানে কিছু ওয়ান-লাইনার রয়েছে (এবং সিএসভিতে টাইপ তথ্য হারাতে একটি নোট):

require 'csv'

rows = [[1,2,3],[4,5]]                    # [[1, 2, 3], [4, 5]]

# To CSV string
csv = rows.map(&:to_csv).join             # "1,2,3\n4,5\n"

# ... and back, as String[][]
rows2 = csv.split("\n").map(&:parse_csv)  # [["1", "2", "3"], ["4", "5"]]

# File I/O:
filename = '/tmp/vsc.csv'

# Save to file -- answer to your question
IO.write(filename, rows.map(&:to_csv).join)

# Read from file
# rows3 = IO.read(filename).split("\n").map(&:parse_csv)
rows3 = CSV.read(filename)

rows3 == rows2   # true
rows3 == rows    # false

দ্রষ্টব্য: সিএসভি সমস্ত ধরণের তথ্য হারাতে পারে, আপনি বেসিক ধরণের তথ্য সংরক্ষণ করতে JSON ব্যবহার করতে পারেন, বা সমস্ত ধরণের তথ্য সংরক্ষণের জন্য ভার্বোজ (তবে আরও সহজেই মানব-সম্পাদনযোগ্য) ওয়াইএএমএল যেতে পারেন - উদাহরণস্বরূপ, আপনার যদি তারিখের প্রকারের প্রয়োজন হয় যা হয়ে যাবে CSV এবং JSON এ স্ট্রিং।


9

@ বোল্ডার_রবির উত্তরে বিল্ডিং করা, এটি আমি যা খুঁজছি তা অনুমান করে আমার সংক্ষেপে us_ecoসিএসভি টেবিল রয়েছে।

CSV.open('outfile.txt','wb', col_sep: "\t") do |csvfile|
  csvfile << us_eco.first.keys
  us_eco.each do |row|
    csvfile << row.values
  end
end

Https://gist.github.com/tamouse/4647196 এ সংক্ষিপ্তসার আপডেট করেছেন


2

এ নিয়ে আমি লড়াই করছি। এটি আমার গ্রহণ:

https://gist.github.com/2639448 :

require 'csv'

class CSV
  def CSV.unparse array
    CSV.generate do |csv|
      array.each { |i| csv << i }
    end
  end
end

CSV.unparse [ %w(your array), %w(goes here) ]

বিটিডব্লিউ, জেআরবিতে প্রি-তে বহু-মাত্রিক অ্যারে থেকে সাবধান থাকুন। [ %w(your array), %w(goes here) ]দেখতে সুন্দর লাগবে না। github.com/pry/pry/issues/568
ফেলিক্স রাবে
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.