我写了一个快速方法,确认来自网页的数据是否正确排序:
def subsort_columns(*columns)
columns.transpose.sort
end
适用于基本测试。现在,已经引入了复杂的子类,我很确定我还需要使用数组,因为不能保证哈希以特定的顺序返回。在这种情况下,输入的顺序代表子顺序优先级。
# `columns_sort_preferences` is an Array in the form of:
# [[sort_ascending_bool, column_data]]
# i.e.
# subsort_columns([true, column_name], [false, column_urgency], [true, column_date])
# Will sort on name ascending, then urgency descending, and finally date ascending.
def subsort_columns(*columns_sort_preferences)
end
这就是我被困住的地方。我想干净利落地做到这一点,但除了为任何父类排序中出现的每个子排序推出一个循环之外,我不能想出任何东西......但这听起来不对。
随意提供更好的建议,因为我不依赖于此实现。
以下是一些测试数据:
a = [1,1,1,2,2,3,3,3,3]
b = %w(a b c c b b a b c)
c = %w(x z z y x z z y z)
subsort_columns([true, a], [false, b], [false, c])
=> [[1, 'c', 'z'],
[1, 'b', 'z'],
[1, 'a', 'x'],
[2, 'c', 'y'],
[2, 'b', 'x'],
[3, 'c', 'z'],
[3, 'b', 'z'],
[3, 'b', 'y'],
[3, 'a', 'z']]
标记为重新打开,因为我已在我们的代码库中我提供as my own answer 的函数上方的注释中链接到此问题。更不用说我从an answer here那里得到的帮助,清楚地显示了我的问题的解决方案,我想给予我一个正确方向的小费。请不要删除这个问题,这对我很有帮助。如果你不同意,至少留下一条评论,说明你不清楚的事情。
答案 0 :(得分:1)
a = [1,1,1,2,2,3,3,3,3]
b = %w(a b c c b b a b c)
c = %w(x z z y x z z y z)
sorted = [a, b, c].transpose.sort do |el1, el2|
[el1[0], el2[1], el2[2]] <=> [el2[0], el1[1], el1[2]]
end
对于下行列,反转太空船操作员的左右元素。结果:
[[1, "c", "z"],
[1, "b", "z"],
[1, "a", "x"]
[2, "c", "y"],
[2, "b", "x"],
[3, "c", "z"],
[3, "b", "z"],
[3, "b", "y"],
[3, "a", "z"]]
答案 1 :(得分:0)
执行此操作的一种方法是以相反的顺序执行一系列“stable sorts”。从内部排序开始,然后向外部排序。稳定属性意味着内部排序顺序保持不变。
不幸的是,Ruby的sort
不稳定。但请参阅this question了解解决方法。
答案 2 :(得分:0)
# Sort on each entry in `ticket_columns`, starting with the first column, then second, etc.
# Complex sorts are supported. If the first element in each `ticket_columns` is a true/false
# boolean (specifying if an ascending sort should be used), then it is sorted that way.
# If omitted, it will sort all ascending.
def _subsort_columns(*ticket_columns)
# Is the first element of every `ticket_column` a boolean?
complex_sort = ticket_columns.all? { |e| [TrueClass, FalseClass].include? e[0].class }
if complex_sort
data = ticket_columns.transpose
sort_directions = data.first
column_data = data[1..-1].flatten 1
sorted = column_data.transpose.sort do |cmp_first, cmp_last|
cmp_which = sort_directions.map { |b| b ? cmp_first : cmp_last }
cmp_these = sort_directions.map { |b| b ? cmp_last : cmp_first }
cmp_left, cmp_right = [], []
cmp_which.each_with_index { |e, i| cmp_left << e[i] }
cmp_these.each_with_index { |e, i| cmp_right << e[i] }
cmp_left <=> cmp_right
end
sorted
else
ticket_columns.transpose.sort
end
end