Reputation: 1389
I need to sort (ascending order) a table by a field.
This is my table:
vTable=Text::Table.new
vTable.head= ["Value", "Rest", "NumberRun"]
I store my data in the table inside a loop
lp= [value, rest, num]
vTable.rows << lp
After completing my table, it looks like:
33183 | 109 | 5.10.0.200
34870 | 114 | 5.4.1.100
28437 | 93 | 5.6.0.050
31967 | 105 | 5.6.2.500
29942 | 98 | 5.7.2.900
I would like to sort, ascending order, this table by "NumberRun" considering that 5.10.0.200 is bigger than 5.7.2.900.
My idea was to remove "." from "NumberRun", convert it into a number, and then sort. In this way 5.10.x > 5.9.x
Upvotes: 1
Views: 167
Reputation: 7685
You can sort the rows the following way. It uses the Array#sort_by!()
method, which was introduced with Ruby 1.9.2.
vTable.rows.sort_by! { |_,_,num| num.split('.').map(&:to_i) }
It also uses Destructuring for the block parameters of sort_by!()
.
For Ruby versions older than 1.9.2 you can sort the rows
and reassign them.
vTable.rows = vTable.rows.sort_by { |_,_,num| num.split('.').map(&:to_i) }
Upvotes: 1
Reputation: 1281
I have created a NumberRun class for you that can do the comparision.
#number_run.rb
class NumberRun
include Comparable
attr_accessor :run_number
def initialize(str)
@run_number = str
end
def <=> str1
str_split = @run_number.split(".")
str1_split = str1.run_number.split(".")
output = 0
str_split.each_with_index do |num, index|
if((num.to_i <=> str1_split[index].to_i) != 0 && index != (str_split.count - 1))
output = (num.to_i <=> str1_split[index].to_i)
break
elsif index == (str_split.count - 1)
output = (num.to_i <=> str1_split[index].to_i)
end
end
output
end
end
For an example:
a = [
NumberRun.new('5.10.0.200'),
NumberRun.new('5.4.1.100'),
NumberRun.new('5.6.0.050'),
NumberRun.new('5.6.2.500'),
NumberRun.new('5.7.2.900')
]
a.sort.map(&:run_number)
Upvotes: 0