1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
|
class Array
def order_by(order)
attribute, direction = order.first
self.sort{ |a,b|
sa, sb = a.send(attribute.to_sym).to_s, b.send(attribute.to_sym).to_s
if ((sa.downcase <=> sb.downcase) == 0)
then sa <=> sb
else
na, nb = self.class.check_regexp(sa, sb)
na <=> nb
end
}.tap do |items|
items.reverse! if direction.to_sym == :desc
end
end
private
# TODO : Puts in a gem this development
def self.check_regexp(sa, sb)
regexp = /(^|\D+)(\d+|(\D$))/
ma, mb = multireg(regexp,sa), self.multireg(regexp,sb)
it = 0
equal = 0
ret = ["",""]
numeric = /(\d+)/
while (it < [ma.size,mb.size].min) and (equal==0)
if (ma[it] and mb[it]) and (ma[it][1] and mb[it][1]) \
and (numeric.match ma[it][0] and numeric.match mb[it][0])
l = [ma[it][2].size,mb[it][2].size].max
ret = [self.format(ma[it], l), self.format(mb[it], l)]
else
ret = [ma[it][0].downcase, mb[it][0].downcase]
end
equal = ret[0] <=> ret[1]
it+=1
end
return ret[0], ret[1]
end
def self.multireg rgpx, str
result = []
while rgpx.match str
result.push rgpx.match(str)
str = rgpx.match(str).post_match
end
result
end
def self.format(match_data, length)
match_data[1].gsub("_", "").downcase + ("%0#{length}d" % match_data[2].to_i)
end
end
|