我想使用Accelerate框架扩展[Float]和[Double],但每个都需要不同的实现。
我尝试了显而易见的事情:
extension Array<Float> {
}
并收到此错误:
&#34;必须在非专用通用上声明约束扩展 type&#39; Array&#39;具有由&#39;其中&#39;指定的约束。条款&#34;
以这种方式扩展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
}
}
答案 0 :(得分:116)
如果只想扩展特定类型的数组。您应该扩展_ArrayType协议。
extension _ArrayType where Generator.Element == Int {
func doSomething() {
...
}
}
如果你扩展Array
,你只能确保你的元素符合其他协议。即:
extension Array where Element: Equatable {
func doSomething() {
...
}
}
<强>更新: 使用Swift 3.1 https://github.com/apple/swift/blob/master/CHANGELOG.md
extension Array where Element == Int {
func doSomething() {
...
}
}
答案 1 :(得分:28)
extension Collection where Iterator.Element == Int {
// `Collection` can be `Sequence`, etc
}
答案 2 :(得分:15)
怎么样
extension CollectionType where Generator.Element == Double {
}
或者如果你想再多一点:
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
适用于Double
和Float
或您符合协议ArithmeticType
和FloatLiteralConvertible
的任何其他类型。如果您需要访问数组的特定索引,请将SequenceType
更改为CollectionType
,因为您无法使用序列执行此操作。
答案 3 :(得分:4)
所以我没有正确地阅读这个问题。 data: [[1,"1227.14","27.07"],[2,"1530.40","28.07"],[3,"1235.46","29.07"],[4,"1192.65","30.07"],[5,"1599.85","31.07"],[6,"1350.35","01.08"]],
是由Double,Float和CGFloat实现的现有协议,所以
是。我昨天才开始向SequenceType添加一个函数,其中元素必须是FloatingPointType
。这是将元素限制为Equatable
您需要使用where子句。这是我的功能。
Float
注意我无法为数组工作,但无论如何,SequenceType更通用。
答案 4 :(得分:4)
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)
答案 5 :(得分:3)
如果您只想扩展特定的Array
,则必须为每种类型使用协议:
protocol DoubleValue {
var value: Double { get }
}
extension Double: DoubleValue {
var value: Double { return self }
}
extension Array where Element: DoubleValue {
// use the value property
}
// the same for Float
protocol FloatValue {
var value: Float { get }
}
extension Float: FloatValue {
var value: Float { return self }
}
extension Array where Element: FloatValue {
// use the value property
}
答案 6 :(得分:0)
这对我有用。我正在使用Swift 5。
扩展数组,其中Iterator.Element == Float { }
答案 7 :(得分:0)
这就是我使用 Swift 5
时的效果:
extension Array where ArrayLiteralElement == Float {
}