Skip to content

Instantly share code, notes, and snippets.

@davidbella
Created October 3, 2013 16:03
Show Gist options
  • Save davidbella/6812287 to your computer and use it in GitHub Desktop.
Save davidbella/6812287 to your computer and use it in GitHub Desktop.
Ruby: Version sort (bad, incomplete)
require 'pp'
class Array
def version_sort
version_sorted = []
versions = self.collect do |filename|
filename =~ /^foo-(.*)\.ext$/
versions = $1.split('.')
end
# Pull the greatest length of each version piece - major, minor, and patch
max_major = versions.collect {|version| version[0]}.compact.
max_by {|word| word.length}
max_minor = versions.collect {|version| version[1]}.compact.
max_by {|word| word.length}
max_patch = versions.collect {|version| version[2]}.compact.
max_by {|word| word.length}
# pp max_major
# pp max_minor
# pp max_patch
# Pull out the length of the max length'ed version number
major_length = max_major.length
# For minor, since we include letters, we are padding out _two extra_
# _characters_ for every non-digit we see - We will see why soon
minor_length = max_minor.length + 2 * max_minor.scan(/\D/).count
patch_length = max_patch.length
# pp major_length
# pp minor_length
# pp patch_length
versions.sort do |a, b|
p a
a[1] = a[1] ? a[1].to_s : 0.to_s
new_a1 = a[1].gsub(/(\D)/) {|match| match.ord.to_s.rjust(minor_length / 2, '0')}
p new_a1
a[2] = a[2] ? a[2].to_s : 0.to_s
new_a = "%0.*d%0.*d" %[major_length, a[0], minor_length, new_a1.to_i, patch_length, a[2]]
p new_a
b[1] = b[1] ? b[1].to_s : 0.to_s
new_b1 = b[1].gsub(/(\D)/) {|match| match.ord.to_s.rjust(minor_length / 2, '0')}
b[2] = b[2] ? b[2].to_s : 0.to_s
new_b = "%0.*d%0.*d" %[major_length, b[0], minor_length, new_b1.to_i, patch_length, b[2]]
new_a <=> new_b
end
end
end
filenames = [
"foo-1.10.2.ext",
"foo-1.11.ext",
"foo-1.3.ext",
"foo-1.50.ext",
"foo-1.8.7.ext",
"foo-1.9.3.ext",
"foo-1.ext",
"foo-10.1.ext",
"foo-10.ext",
"foo-100.ext",
"foo-13.ext",
"foo-2.0.0.ext",
"foo-2.0.1.ext",
"foo-2.0.ext",
"foo-2.007.ext",
"foo-2.01.ext",
"foo-2.012b.ext",
"foo-2.01a.ext",
"foo-2.0a.ext",
"foo-2.0b.ext",
"foo-2.1.ext",
"foo-25.ext",
"foo-6.ext",
]
version_sorted_filenames = [
"foo-1.ext",
"foo-1.3.ext",
"foo-1.8.7.ext",
"foo-1.9.3.ext",
"foo-1.10.2.ext",
"foo-1.11.ext",
"foo-1.50.ext",
"foo-2.0.ext",
"foo-2.0a.ext",
"foo-2.0b.ext",
"foo-2.0.0.ext",
"foo-2.0.1.ext",
"foo-2.01.ext",
"foo-2.1.ext",
"foo-2.01a.ext",
"foo-2.007.ext",
"foo-2.012b.ext",
"foo-6.ext",
"foo-10.ext",
"foo-10.1.ext",
"foo-13.ext",
"foo-25.ext",
"foo-100.ext",
]
p filenames.version_sort
#assert_equal filenames.version_sort, version_sorted_filenames
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment