[lnkForumImage]
TotalShareware - Download Free Software

Confronta i prezzi di migliaia di prodotti.
Asp Forum
 Home | Login | Register | Search 


 

Forums >

comp.lang.ruby

Beginner questions: sorting csv files

Michael Sc

2/2/2007 4:52:00 PM

Hello,
I am a newbie with Ruby and I had a couple of questions while
manipulating csv files. How would I do a multiple column sort? I have
a file that needs to be sorted by the 3rd column, then 1st, then second.
I understand how to do one sort for the csv file but I was unsure of how
to do multiple.

Also,How would I to do a percentage change between two numbers in a
column?

Thank you very much. I know these are easy questions but I am still
learning how to program in Ruby.

--
Posted via http://www.ruby-....

16 Answers

William James

2/2/2007 10:03:00 PM

0

On Feb 2, 10:52 am, Michael Sc <michael.schat...@gmail.com> wrote:
> Hello,
> I am a newbie with Ruby and I had a couple of questions while
> manipulating csv files. How would I do a multiple column sort? I have
> a file that needs to be sorted by the 3rd column, then 1st, then second.
> I understand how to do one sort for the csv file but I was unsure of how
> to do multiple.
>
> Also,How would I to do a percentage change between two numbers in a
> column?
>
> Thank you very much. I know these are easy questions but I am still
> learning how to program in Ruby.
>
> --
> Posted viahttp://www.ruby-....


[ [9,'ash','cube'],
[8,'blue','cube'],
[3,'mauve','frustrum'],
[8,'green','cube']
].sort_by{|a| a.values_at( 2,0,1 ) }.
each{|a| p a }

--- output -----
[8, "blue", "cube"]
[8, "green", "cube"]
[9, "ash", "cube"]
[3, "mauve", "frustrum"]

Michael Sc

2/2/2007 10:27:00 PM

0

Thank you very much. I did not realize it was so simple. Do you know
how to refer to prior lines to make calculations?

--
Posted via http://www.ruby-....

William James

2/2/2007 10:46:00 PM

0

On Feb 2, 4:26 pm, Michael Sc <michael.schat...@gmail.com> wrote:
> Thank you very much. I did not realize it was so simple. Do you know
> how to refer to prior lines to make calculations?
>
> --
> Posted viahttp://www.ruby-....

a =
[ ['alloy', 1.414],
['malign', 1.732],
['smudge', 2.0],
['smack', 2.236]
]

0.upto( a.size - 2 ) {|i|
puts "Change from line #{i} to line #{i+1}: #{ (a[i+1][1] - a[i][1]) / a[i][1] * 100 }%"
}

Michael Sc

2/3/2007 3:54:00 AM

0

William James wrote:
> On Feb 2, 4:26 pm, Michael Sc <michael.schat...@gmail.com> wrote:
>> Thank you very much. I did not realize it was so simple. Do you know
>> how to refer to prior lines to make calculations?
>>
>> --
>> Posted viahttp://www.ruby-....
>
> a =
> [ ['alloy', 1.414],
> ['malign', 1.732],
> ['smudge', 2.0],
> ['smack', 2.236]
> ]
>
> 0.upto( a.size - 2 ) {|i|
> puts "Change from line #{i} to line #{i+1}:> #{ (a[i+1][1] - a[i][1]) / a[i][1] * 100 }%"
> }
Thank you very much. I just had one more question about this then. How
would I write this to its own csv file?

require 'csv'
outfile = File.open('newfile.csv', 'wb')
x=CSV.open("oldfile.csv", "r")
x.sort_by{|a| a.values_at( 2,0,1 ) }.each{|a| outfile.print a }
outfile.close

I tried outfile.p(doesn't work), outfile.print(takes out the commas) and
outfile.put(takes out the breaks). I know this should be incredibly
easy but I am clearly missing something.

--
Posted via http://www.ruby-....

William James

2/3/2007 7:55:00 AM

0

On Feb 2, 9:53 pm, Michael Sc <michael.schat...@gmail.com> wrote:
> William James wrote:
> > On Feb 2, 4:26 pm, Michael Sc <michael.schat...@gmail.com> wrote:
> >> Thank you very much. I did not realize it was so simple. Do you know
> >> how to refer to prior lines to make calculations?
>
> >> --
> >> Posted viahttp://www.ruby-....
>
> > a =
> > [ ['alloy', 1.414],
> > ['malign', 1.732],
> > ['smudge', 2.0],
> > ['smack', 2.236]
> > ]
>
> > 0.upto( a.size - 2 ) {|i|
> > puts "Change from line #{i} to line #{i+1}:> > #{ (a[i+1][1] - a[i][1]) / a[i][1] * 100 }%"
> > }
>
> Thank you very much. I just had one more question about this then. How
> would I write this to its own csv file?
>
> require 'csv'
> outfile = File.open('newfile.csv', 'wb')
> x=CSV.open("oldfile.csv", "r")
> x.sort_by{|a| a.values_at( 2,0,1 ) }.each{|a| outfile.print a }
> outfile.close
>
> I tried outfile.p(doesn't work), outfile.print(takes out the commas) and
> outfile.put(takes out the breaks). I know this should be incredibly
> easy but I am clearly missing something.

Before writing each record (i.e., each array of fields) to the file,
it must first be converted to a proper csv string.
The 'csv' package has a method for doing this, I presume.

If you don't wan't to use that, try this:


class Array
def to_csv
s = ''
map { |item|
str = item.to_s
# Quote the string if it contains the field-separator or
# a " or a newline or a carriage-return, or if it has leading or
# trailing whitespace.
if str.index( "," ) or /^\s|["\r\n]|\s$/.match(str)
str = '"' + str.gsub( /"/, '""' ) + '"'
end
str
}.join( "," )
end
end

puts [ 674, "yes", "Jones,Tom", 'foo"bar', " space " ].to_csv

--- output -----
674,yes,"Jones,Tom","foo""bar"," space "

Michael Sc

2/3/2007 1:28:00 PM

0

Thank you very much.

--
Posted via http://www.ruby-....

Michael Sc

2/6/2007 3:14:00 PM

0

Hey,
I just had another question on these csv files. Is there anyway I could
save sorted files using the fastercsv library? Thanks again for all of
the help. I am having trouble figuring out how to use the libraries.

--
Posted via http://www.ruby-....

Drew Olson

2/6/2007 3:28:00 PM

0

Michael Sc wrote:
> Hey,
> I just had another question on these csv files. Is there anyway I could
> save sorted files using the fastercsv library? Thanks again for all of
> the help. I am having trouble figuring out how to use the libraries.

Assuming your csv file is stored as "my_array":

require 'rubygems'
require 'faster_csv'

FCSV.open("output.csv","w") do |out|
my_array.each{|row| out << row}
end

--
Posted via http://www.ruby-....

Michael Sc

2/6/2007 3:49:00 PM

0

Drew Olson wrote:
> Assuming your csv file is stored as "my_array":
>
> require 'rubygems'
> require 'faster_csv'
>
> FCSV.open("output.csv","w") do |out|
> my_array.each{|row| out << row}
> end
Thank you very much.

--
Posted via http://www.ruby-....

Drew Olson

2/6/2007 3:51:00 PM

0

Michael Sc wrote:
> Hello,
> I am a newbie with Ruby and I had a couple of questions while
> manipulating csv files. How would I do a multiple column sort? I have
> a file that needs to be sorted by the 3rd column, then 1st, then second.
> I understand how to do one sort for the csv file but I was unsure of how
> to do multiple.
>
> Also,How would I to do a percentage change between two numbers in a
> column?
>
> Thank you very much. I know these are easy questions but I am still
> learning how to program in Ruby.

Come to think of it, I'd do the whole thing using FasterCSV. When
available, I like to use a well known library where the hard work has
already been done for me :)

require 'rubygems'
require 'faster_csv'

mycsv = FCSV.read("myfile.csv")

FCSV.open("output.csv","w") do |out|
mycsv.sort{|a,b| [a[2],a[0],a[1]] <=> [b[2],b[0],b[1]]}.each |row|
out << row
end
end

--
Posted via http://www.ruby-....