gpt4 book ai didi

arrays - 如何一般地处理枚举(集合)的数组和字典的不同返回类型?

转载 作者:可可西里 更新时间:2023-11-01 01:06:50 25 4
gpt4 key购买 nike

作为 Swift 的新手,作为练习,我正在尝试编写一个 Swift 等效于 underscore.js 的 _.each:

_.each({foo: true, bar: false}, function(value, key) {...}
_.each([true, false], function(value, key) {...}

但事实证明这很困难,因为 enumerate(collection) 会为字典和数组返回不同类型的结果:

for (indexInt, (key, value)) enumerate(["foo": true]) {...}
for (key, value) enumerate([true]) {...}

如果不显式检查通用集合类的 ArrayDictionary,我该如何处理这两种不同的返回类型?

返回类型检查将失败,因为下面两个示例应该被区别对待,但从 enumerate() 返回等效类型:

for (indexInt, (key, value)) enumerate(["foo": true]) {...}
for (indexInt, (key, value)) enumerate([("foo", true")]) {...}

另外,FWIW,$.swift 似乎在赌这个:

https://github.com/ankurp/Dollar.swift/blob/master/Dollar/Dollar/Dollar.swift#L193-L217

编辑:格式化。还有..

一个 splinter 的通用实现

func each<C: Collection>(collection: C, fn: (Any, Any) -> ()) -> C {
// On next line... Error: Tuple pattern cannot match values of the non-tuple type 'C.GeneratorType.Element'
for (_, (k, v)) in enumerate(collection) {
if let innerV = collection[innerK] {
fn(innerV, k)
}
}
return collection
}
var ret = each(["foo":true, "bar":false]) { println("Key \($1), Value:\($0)") }

有效的字典实现

func eachDictionary<K,V>(collection: Dictionary<K, V>, fn: (V, K) -> ()) -> Dictionary<K, V> {
for (_, (k, v)) in enumerate(collection) {
fn(v, k)
}
return collection
}
var retDictionary = eachDictionary(["foo":true, "bar":false]) { println("Key \($1), Value:\($0)") }

一个有效的 Array 实现

func each<V>(collection: V[], fn: (V, Int) -> ()) -> V[] {
for (k, v) in enumerate(collection) {
fn(v, k)
}
return collection
}
var retArray = each([true, false]) { println("Key \($1), Value:\($0)") }

编辑 2:更新示例以使用重载。 我特别想问一下,是否有一种通用的收集协议(protocol)方法可以实现这一点,而不需要对每种收集类型都进行一次性处理?

编辑 3:我尝试了以下操作(我不得不在空数组的情况下添加更多输入,这样它就不会提示回调参数不可打印)但是......

  1. 现在字典失败(传递 (K,V) 作为值)
  2. [(V1,V2)] 情况失败
  3. 我非常想找到一种方法来使用泛型 (K, V) 而不是 (Any, Any)

代码:

func each<C: Collection>(collection: C, fn: (Any, Any) -> ()) -> C {
for (k, v) in enumerate(collection) {
if let (key, value) = v as? (Any, Any) {
fn(value, key)
} else {
fn(v, k)
}
}
return collection
}
var ret = each(["foo":true, "bar":false]) { println("1: Key \($1), Value:\($0)") }
var arr : String[] = []
var retOne = each(arr) { println("2: Key \($1), Value:\($0)") }
var retTwo = each([true, false]) { println("3: Key \($1), Value:\($0)") }

最佳答案

JavaScript 和 Swift 之间最大的区别之一是您可以定义具有相同名称但具有不同签名(重载)的(函数|方法)。好好利用吧。

class $ {
class func map<K:Hashable,V,R>
(dictionary:[K:V], block:(V,K)->R)->[K:R] {
var result = [K:R]()
for (k, v) in dictionary {
result[k] = block(v, k)
}
return result
}
class func map<V,R>
(array:[V], block:(V,Int)->R)->[R] {
var result = [R]()
for (k, v) in enumerate(array) {
result.append(block(v, k))
}
return result
}
class func each<K:Hashable,V,R>
(dictionary:[K:V], block:(V,K)->R) {
for (k, v) in dictionary { block(v, k) }
}
class func each<V,R>
(array:[V], block:(V,Int)->R) {
for (k, v) in enumerate(array) { block(v, k) }
}
}

println($.map(["zero":0, "one":1], { n,_ in n+1 }))
println($.map([0,1], { n,_ in n+1 }))
$.each(["zero":0, "one":1]) { println("\($1) => \($0)") }
$.each([0, 1]) { println("\($1) => \($0)") }

关于arrays - 如何一般地处理枚举(集合)的数组和字典的不同返回类型?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24745712/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com