是否有模拟 - (NSArray *)keysSortedByValueUsingSelector :( SEL)比较器在swift?
如何在不转换为NSDictionary的情况下执行此操作?
我试过这个,但似乎不是一个好的解决方案。
var values = Array(dict.values)
values.sort({
$0 > $1
})
for number in values {
for (key, value) in dict {
if value == number {
println(key + " : \(value)");
dict.removeValueForKey(key);
break
}
}
}
示例:
var dict = ["cola" : 10, "fanta" : 12, "sprite" : 8]
dict.sortedKeysByValues(>) // fanta (12), cola(10), sprite(8)
答案 0 :(得分:26)
只需一行代码即可按Swift 4中的值对字典进行排序:
<a href="mailto:info@atmox.nl">info@atmox.nl</a>
答案 1 :(得分:21)
你可以使用这样的东西:
var dict = ["cola" : 10, "fanta" : 12, "sprite" : 8]
var myArr = Array(dict.keys)
var sortedKeys = sort(myArr) {
var obj1 = dict[$0] // get ob associated w/ key 1
var obj2 = dict[$1] // get ob associated w/ key 2
return obj1 > obj2
}
myArr // ["fanta", "cola", "sprite"]
答案 2 :(得分:20)
尝试:
let dict = ["a":1, "c":3, "b":2]
extension Dictionary {
func sortedKeys(isOrderedBefore:(Key,Key) -> Bool) -> [Key] {
return Array(self.keys).sort(isOrderedBefore)
}
// Slower because of a lot of lookups, but probably takes less memory (this is equivalent to Pascals answer in an generic extension)
func sortedKeysByValue(isOrderedBefore:(Value, Value) -> Bool) -> [Key] {
return sortedKeys {
isOrderedBefore(self[$0]!, self[$1]!)
}
}
// Faster because of no lookups, may take more memory because of duplicating contents
func keysSortedByValue(isOrderedBefore:(Value, Value) -> Bool) -> [Key] {
return Array(self)
.sort() {
let (_, lv) = $0
let (_, rv) = $1
return isOrderedBefore(lv, rv)
}
.map {
let (k, _) = $0
return k
}
}
}
dict.keysSortedByValue(<)
dict.keysSortedByValue(>)
更新:
更新了新的数组语法并从beta 3中排序语义。请注意,我使用sort
而不是sorted
来最小化数组复制。通过查看早期版本并将sort
替换为sorted
并将KeyType[]
修改为[KeyType]
更新为Swift 2.2:
将类型从KeyType
更改为Key
和ValueType
更改为Value
。使用新sort
内置到Array
代替sort(Array)
注意使用sortInPlace
代替sort
答案 3 :(得分:14)
这应该根据值给你排序的键,并且更清洁一点:
var sortedKeys = Array(dict.keys).sorted({dict[$0] < dict[$1]})
答案 4 :(得分:7)
我认为这是按值对Swift字典进行排序的最简单方法。
let dict = ["apple":1, "cake":3, "banana":2]
let byValue = {
(elem1:(key: String, val: Int), elem2:(key: String, val: Int))->Bool in
if elem1.val < elem2.val {
return true
} else {
return false
}
}
let sortedDict = dict.sort(byValue)
答案 5 :(得分:5)
按字典的值对键进行排序实际上比最初看起来更简单:
let yourDict = ["One": "X", "Two": "B", "Three": "Z", "Four": "A"]
let sortedKeys = yourDict.keys.sort({ (firstKey, secondKey) -> Bool in
return yourDict[firstKey] < yourDict[secondKey]
})
就是这样!真的没什么了不起的。我还没有找到一种更快捷的方法。
答案 6 :(得分:5)
很多答案,这是一个单行。我喜欢它,因为它充分利用了原生的Swift迭代函数,并且不使用变量。这应该有助于优化者发挥其魔力。
return dictionary.keys.sort({ $0 < $1 }).flatMap({ dictionary[$0] })
请注意使用flatMap,因为下载字典会返回一个可选值。在实践中,这应该永远不会返回nil,因为我们从字典本身获取密钥。 flatMap
只是为了确保结果不是一个选项数组。如果您的数组的关联值应该是可选的,则可以使用map
代替。
答案 7 :(得分:5)
let dict = ["b":2,"a":1,"c":3]
(Array(dict).sorted{$0.1 < $1.1}).forEach{(k,v) in print("\(k):\(v)")}
//Output: a:1, b:2, c:3
使用.forEach
- &gt;换掉.map
功能编程
extension Dictionary where Value:Comparable {
var sortedByValue:[(Key,Value)] {return Array(self).sorted{$0.1 < $1.1}}
}
extension Dictionary where Key:Comparable {
var sortedByKey:[(Key,Value)] {return Array(self).sorted{$0.0 < $1.0}}
}
["b":2,"a":1,"c":3].sortedByKey//a:1, b:2, c:3
["b":2,"a":1,"c":3].sortedByValue//a:1, b:2, c:3
答案 8 :(得分:4)
使用 Swift 5.2 内部处理“已排序”:
var unsortedDict = ["cola" : 10, "fanta" : 12, "sprite" : 8]
// sorting by value
let sortedDictByValue = unsortedDict.sorted{ $0.value > $1.value } // from lowest to highest using ">"
print("sorted dict: \(sortedDictByValue)")
// result: "sorted dict: [(key: "fanta", value: 12), (key: "cola", value: 10), (key: "sprite", value: 8)]\n"
// highest value
print(sortedDictByValue.first!.key) // result: fanta
print(sortedDictByValue.first!.value) // result: 12
// lowest value
print(sortedDictByValue.last!.key) // result: sprite
print(sortedDictByValue.last!.value) // result: 8
// by index
print(sortedDictByValue[1].key) // result: cola
print(sortedDictByValue[1].value) // result: 10
// sorting by key
let sortedDictByKey = unsortedDict.sorted{ $0.key < $1.key } // in alphabetical order use "<"
// alternative:
// let sortedDictByKey = unsortedDict.sorted{ $0 < $1 } // without ".key"
print("sorted dict: \(sortedDictByKey)")
// result: "sorted dict: [(key: "cola", value: 10), (key: "fanta", value: 12), (key: "sprite", value: 8)]\n"
// highest value
print(sortedDictByKey.first!.key) // result: cola
print(sortedDictByKey.first!.value) // result: 10
// lowest value
print(sortedDictByKey.last!.key) // result: sprite
print(sortedDictByKey.last!.value) // result: 8
// by index
print(sortedDictByKey[1].key) // result: fanta
print(sortedDictByKey[1].value) // result: 12
答案 9 :(得分:4)
如果您希望输出是元组形式的键值对数组,按值排序,则以下内容可能很有用。
var dict = ["cola" : 10, "fanta" : 12, "sprite" : 8]
let sortedArrByValue = dict.sorted{$0.1 > $1.1}
print(sortedArrByValue) // output [(key: "fanta", value: 12), (key: "cola", value: 10), (key: "sprite", value: 8)]
答案 10 :(得分:3)
将其强制转换为NSDictionary,然后调用该方法。在ObjC中使用@selector
的任何地方,您都可以在Swift中使用String。所以它看起来像这样:
var dict = ["cola" : 10, "fanta" : 12, "sprite" : 8]
let sortedKeys = (dict as NSDictionary).keysSortedByValueUsingSelector("compare:")
或
let sortedKeys2 = (dict as NSDictionary).keysSortedByValueUsingComparator
{
($0 as NSNumber).compare($1 as NSNumber)
}
答案 11 :(得分:3)
从Swift 3开始,为了根据值对键进行排序,下面看起来很有希望:
var keys = Array(dict.keys)
keys.sortInPlace { (o1, o2) -> Bool in
return dict[o1]! as! Int > dict[o2]! as! Int
}
答案 12 :(得分:2)
var dict = ["cola" : 10, "fanta" : 12, "sprite" : 8]
let arr = dic.sort{ (d1,d2)-> Bool in
if d1.value > d2.value {
retrn true
}
}.map { (key,value) -> Int in
return value
}
采用一种干净的实现方式。 print(“ arr is:(arr)”)
答案 13 :(得分:1)
Swift 3中的以下方式按升序对值进行排序:
for (k,v) in (Array(dict).sorted {$0.1 < $1.1}) {
print("\(k):\(v)")
}
答案 14 :(得分:1)
使用字典作为值对字典进行排序(嵌套字典)
var students: [String: [String: Any?]] = ["16CSB40" : ["Name": "Sunitha", "StudentId": "16CSB40", "Total": 90], "16CSB41" : ["Name": "Vijay", "StudentId": "16CSB40", "Total": 80], "16CSB42" : ["Name": "Tony", "StudentId": "16CSB42", "Total": 95]] // Sort this dictionary with total value
let sorted = students.sorted { (($0.1["Total"] as? Int) ?? 0) < (($1.1["Total"] as? Int) ?? 0) }
print(sorted) //Sorted result
答案 15 :(得分:1)
SWIFT 3:
使用一些资源我将这个精美的短代码放在一起。
dictionary.keys.sorted{dictionary[$0]! < dictionary[$1]!}
这将返回按其值排序的字典键数组。它完美无缺。字典为空时不会抛出错误。在游乐场试试这段代码:
//: Playground - noun: a place where people can play
import UIKit
let dictionary = ["four": 4, "one": 1, "seven": 7, "two": 2, "three": 3]
let sortedDictionary = dictionary.keys.sorted{dictionary[$0]! < dictionary[$1]!}
print(sortedDictionary)
// ["one", "two", "three", "four", "seven"]
let emptyDictionary = [String: Int]()
let emptyDictionarySorted = emptyDictionary.keys.sorted{emptyDictionary[$0]! < emptyDictionary[$1]!}
print(emptyDictionarySorted)
// []
如果您想了解为什么代码使用$ 0,$ 1并且在“已排序”方法后甚至没有括号,请查看此帖子 - https://stackoverflow.com/a/34785745/7107094
答案 16 :(得分:0)
由于Swift 3.0 Dictionary
具有sorted(by:)
函数,该函数返回元组数组([(Key, Value)]
)。
let sorted = values.sorted(by: { (keyVal1, keyVal2) -> Bool in
keyVal1.value > keyVal2.value
})
答案 17 :(得分:0)
这就是我的做法 - 在这种情况下通过一个名为position的键进行排序。在操场上试试这个:
var result: [[String: AnyObject]] = []
result.append(["name" : "Ted", "position": 1])
result.append(["name" : "Bill", "position": 0])
result
result = sorted(result, positionSort)
func positionSort(dict1: [String: AnyObject], dict2: [String: AnyObject]) -> Bool {
let position1 = dict1["position"] as? Int ?? 0
let position2 = dict2["position"] as? Int ?? 0
return position1 < position2
}
答案 18 :(得分:0)
使用它,然后使用输出键再次遍历字典。
extension Dictionary where Value: Comparable {
func sortedKeysByValue() -> [Key] {
keys.sorted { return self[$0]! < self[$1]! }
}
}
...或者如果您讨厌用力将其解开:)
extension Dictionary where Value: Comparable {
func sortedKeysByValue() -> [Key] {
keys.sorted { (key1, key2) -> Bool in
guard let val1 = self[key1] else { return true }
guard let val2 = self[key2] else { return true }
return val1 < val2
}
}
}