public typealias FailureClosure = (error: NSError?) -> Void public typealias ProgressClosure = (progress: Float32) -> Void public typealias BasicClosure = () -> Void
我想添加一个支持通用数组的闭包类型,但是我似乎无法弄清楚它的语法.这是我能够得到的,但我得到编译时错误“使用未声明的类型”T“@H_502_5@
public typealias ArrayClosure = <T>(array:[T]?) -> Void
有人知道该怎么做吗或者即使有可能吗?@H_502_5@
解决方法
public typealias ArrayClosure<T> = (array:[T]?) -> Void
然后,您将使用它像ArrayClosure< Int>.但目前还不合法.@H_502_5@
也就是说,我不太推荐这些类型的别名.他们比他们照亮更模糊.比较这个签名:@H_502_5@
func foo(onError: FailureClosure)
有:@H_502_5@
func foo(onError: NSError? -> Void)
为了节省几个字符,您强制调用者猜测FailureClosure通过什么.错误或进度标签没有真正帮助您(您仍然需要在…中使用进度).@H_502_5@
一个很有意义的案例是围绕进步的,但我认为你想要的类型是:@H_502_5@
public typealias Progress = Float32
不要误会这里,当创建一个新的类型时,键入别名可以是非常有帮助的.进度是一种恰好像float一样实现的类型.但是,您正在做的很多事情(绝对与ArrayClosure一起使用,并且在其他方面)只是创建新的语法而不创建新的类型,而且更经常是令人困惑而不是有用的.@H_502_5@
要提出您的具体示例,为什么过度使用类型别名可能会导致您过度复制设计:@H_502_5@
func foo(failure: ((error: NSError?) -> ())? = nil)
你是对的,这真的很复杂.比较:@H_502_5@
func foo(failure: NSError -> Void = {_ in return})
这里有两大变化.没有理由有一个失败块可以接受可选错误.总是传递错误(如果没有错误,为什么会失败?).并且没有任何理由阻止故障是可选的.如果你真的想要一个默认值,只要使默认值什么都不做.两个可选项已经消失,所有的使用和实现代码变得更简单.总是仔细考虑一些绝对必须是可选的东西.可选项增加了很多复杂性;不要轻易添加它们.@H_502_5@
就个人而言,我可能会在超负荷的情况下执行此操作,但在许多情况下:@H_502_5@
func foo(#failure: NSError -> Void) { ... } func foo() { foo(failure:{ _ in return }) }
我只是认为这更容易了解发生了什么.但是无论哪种方式都可以.@H_502_5@
EDIT(2014年12月):在写了Swift几个月后,我在下面的评论中更加喜欢@ David的方法,这是为了关闭而使用可选的,但不是错误.特别给出Swift的可选链接语法(failure?()),它通常会变得更加清晰.@H_502_5@
func foo(failure: (NSError -> Void)? = nil)