使用Swift中的where子句扩展数组类型

GSc*_*ivs 70 generics swift swift-extensions swift2

我想使用Accelerate框架扩展[Float]和[Double],但每个都需要不同的实现.

我试过了明显的事:

extension Array<Float> {
}
Run Code Online (Sandbox Code Playgroud)

并得到此错误:

"必须在非特定的泛型类型'Array'上声明约束扩展,并使用'where'子句指定的约束"

以这种方式扩展Swift 2中的泛型类型是否可行?

我现在已经按预期运行了代码.这是一个使用Accelerate框架显示总和的示例.

extension _ArrayType where Generator.Element == Float {

    func quickSum() -> Float {
        var result: Float = 0
        if var x = self as? [Float] {
            vDSP_sve(&x, 1, &result, vDSP_Length(x.count))
        }
        return result
    }
}

extension _ArrayType where Generator.Element == Double {

    func quickSum() -> Double {
        var result: Double = 0
        if var x = self as? [Double] {
            vDSP_sveD(&x, 1, &result, vDSP_Length(x.count))
        }
        return result
    }
}
Run Code Online (Sandbox Code Playgroud)

Huy*_* Le 120

如果只想扩展特定类型的数组.您应该扩展_ArrayType协议.

extension _ArrayType where Generator.Element == Int {

   func doSomething() {
       ... 
   }
}
Run Code Online (Sandbox Code Playgroud)

如果你扩展,Array你只能确保你的元素符合其他协议.即:

extension Array where Element: Equatable {

   func doSomething() {
       ... 
   }
}
Run Code Online (Sandbox Code Playgroud)

更新:使用Swift 3.1 https://github.com/apple/swift/blob/master/CHANGELOG.md

extension Array where Element == Int {

   func doSomething() {
       ... 
   }
}
Run Code Online (Sandbox Code Playgroud)

  • 在swift 3.1中,`扩展数组,其中Element == Int`给出错误**错误:同类型要求使得泛型参数'Element'非泛型扩展数组,其中Element == Int**,给我建议 (15认同)
  • 答案与Swift 2.2完美配合,但_ArrayType在Swift 3中消失了.我们现在应该怎么做? (8认同)
  • Xcode 8.2也是如此.`Element == Int`不起作用 (4认同)

Ben*_* Lu 28

斯威夫特3救援!!

extension Collection where Iterator.Element == Int {
    // `Collection` can be `Sequence`, etc
}
Run Code Online (Sandbox Code Playgroud)


Kam*_*xom 15

怎么样

extension CollectionType where Generator.Element == Double {

}
Run Code Online (Sandbox Code Playgroud)

或者如果你想要更多一点:

protocol ArithmeticType {
    func +(lhs: Self, rhs: Self) -> Self
    func -(lhs: Self, rhs: Self) -> Self
    func *(lhs: Self, rhs: Self) -> Self
    func /(lhs: Self, rhs: Self) -> Self
}

extension Double : ArithmeticType {}
extension Float : ArithmeticType {}

extension SequenceType where Generator.Element : protocol<FloatLiteralConvertible, ArithmeticType> {
    var sum : Generator.Element {
        return reduce(0.0, combine: +)
    }

    var product : Generator.Element {
        return reduce(1.0, combine: *)
    }
}


stride(from: 1.0, through: 10.0, by: 1.0).sum   // 55
[1.5, 2.0, 3.5, 4.0, 5.5].product               // 231
Run Code Online (Sandbox Code Playgroud)

工程与DoubleFloat或您符合协议的任何其他类型的ArithmeticTypeFloatLiteralConvertible.如果您需要访问您的阵列,变化的具体指标SequenceTypeCollectionType作为你不能用序列做到这一点.


小智 5

Xcode 8.2 上的 Swift 3

只需要扩展 Sequence 协议并提供一个 where 语句即可。

let someString = "1, 2, 3, 4, 5, 6, 7, 8"

extension String {        
  func toArrayOfElements() -> [String] {
    return self.components(separatedBy: ", ")
  }        
}

extension Sequence where Iterator.Element == String {        
  func toInt() -> [Int] {            
    return self.map {
      Int($0)!
    }
  }        
}

let arrayOfStrings = someString.toArrayOfElements()    
print(arrayOfStrings)

let arrayOfInts = arrayOfStrings.toInt()    
print(arrayOfInts)
Run Code Online (Sandbox Code Playgroud)