Smalltalk: сортировка коллекции по двум критериям - PullRequest
8 голосов
/ 21 ноября 2011

Как мне отсортировать коллекцию по двум критериям в Cincom VisualWorks?

Пример: у меня есть OrderedCollection, которая содержит людей, и хочу новую коллекцию, которая сортирует людей сначала по возрасту, а затем, если возраст совпадает, сортирует людей по имени.

Надеюсь, вы понимаете мой английский!Спасибо ..

Ответы [ 4 ]

9 голосов
/ 21 ноября 2011

Трэвис Григгс реализовал интересный способ сделать этот вид сортировки намного более кратким способом. Он опубликовал свою работу как TAG-SortFunctions в публичном репозитории Cincom, и я считаю, что она была интегрирована в следующую версию VisualWorks. См. его сообщение в блоге на тему и продолжение для деталей. Используя этот пакет, вы просто напишите что-то вроде этого (не проверено):

люди сортируют: #age sortUp, #name sortUp

8 голосов
/ 21 ноября 2011

Код Шона в порядке, но я предпочитаю, чтобы он был написан таким образом, что более показательно и немного более эффективно:

people sort: [ :a :b |
    a age < b age
        or: [a age = b age and: [ a name < b name ] ]

Идея состоит в том, что блок сортировки должен отвечать true, если элемент a сортируется до item b. С учетом двух ключей, элемент сортируется перед другим элементом, если или его первичный ключ (age) меньше, или первичный ключ такой же, и вторичный ключ (name) меньше.

Это переводит непосредственно в приведенный выше код и может быть легко расширен до третьего или более критериев сортировки (например, либо вторичный ключ меньше, либо он такой же, а третичный ключ меньше).

7 голосов
/ 21 ноября 2011
people sort: [ :a :b |
    a age = b age
        ifTrue: [ a name < b name ]
        ifFalse: [ a age < b age ] ]
6 голосов
/ 21 ноября 2011

Как сказал Рэнди, но он интегрирован в VisualWorks 7.8, и его синтаксис будет следующим: aCollection asSortedCollection: #age по возрастанию, #name по убыванию

, где вы также можете использовать sort: или что-либо еще, что потребуетБлок сортировки.

...