Extend array types using where clause in Swift

Swift 3 on Xcode 8.2

Just need to extend Sequence protocol and provide a where statement.

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)

Swift 3 to the rescue!!

extension Collection where Iterator.Element == Int {
    // `Collection` can be `Sequence`, etc
}

How about

extension CollectionType where Generator.Element == Double {

}

Or If you want a little bit more:

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

Works with Double and Float or any other type that you conform to the protocols ArithmeticType and FloatLiteralConvertible. If you need to access specific indices of your array, change SequenceType to CollectionType as you cannot do this with a sequence.


If you want to extend only array with specific type. You should extend _ArrayType protocol.

extension _ArrayType where Generator.Element == Int {

   func doSomething() {
       ... 
   }
}

If you extend Array you can only make sure your element is conformed some protocol else. i.e:

extension Array where Element: Equatable {

   func doSomething() {
       ... 
   }
}

Updated: With Swift 3.1 https://github.com/apple/swift/blob/master/CHANGELOG.md

extension Array where Element == Int {

   func doSomething() {
       ... 
   }
}