作为学习
Swift的练习,我尝试使用名为comparest的共享方法在Array上创建最小和最大扩展方法.一切都经过测试,效果很好,除了一件事:没有参数,我不能使用最小函数.我已经指定了一个默认参数值nil,但是当我在没有这个参数的情况下调用minimum时,Apple的Swift编译器不喜欢它.
这是我的方法定义.他们编译得很好.
extension Array {
func comparest<C: Comparable>(comparator: T -> C, _ op: (C, C) -> Bool) -> T? {
var min = self.first
for elem in self {
if op(comparator(elem), comparator(min!)) {
min = elem
}
}
return min
}
func minimum<C: Comparable>(var _ comparator: (T -> C)? = nil) -> T? {
if comparator == nil {
comparator = { elem -> C in elem as C }
}
return self.comparest(comparator!, { $0 < $1 })
}
}
(如果你想知道为什么我说比较(比较器!,{$0< $1})而不是比较(比较器!,<),请参阅我的related question.)
如果我说
var array = [3, 4, 1, 9]
var min = array.minimum({ $0 })
一切顺利.但是,我设计了这个方法,以便可以省略传递给minimum的参数,在这种情况下,数组元素本身被用作比较值,例如,
var array = [3, 4, 1, 9]
var min = array.minimum()
编译器讨厌这个.它说“无法将表达式的类型()转换为Int?”.我在这里很无能为力.有什么想法吗?
(暂时不说,参数的原因是你想比较一个属性的值,比如,对象,例如routes.map({$0 as MKRoute}).minimum({$0.distance})将给你最小距离的路线.)
最佳答案 数组中的元素不必是Comparable,这意味着您无法为所有可能的数组编写该函数.
不幸的是,Swift不允许你只扩展数组的子集.在其他功能中,编译器需要额外的类型信息来推断类型C.
其他人也在努力解决同样的问题:
How can we create a generic Array Extension that sums Number types in Swift?
您应该能够使用minimum作为全局函数,而不是使用扩展.