我有两个函数可以做同样的事情。一个有可选的完成块,另一个是异步的:
@MainActor
@objc static func dismiss(_ completion: (() -> Void)? = nil) {
}
@MainActor
@objc static func dismiss() async {
}
当我从另一个@MainActor函数调用这些函数时,编译器似乎无法区分异步版本和非异步版本:
@MainActor
static func myFunc() async {
await dismiss() // works
dismiss() // Error: "Expression is 'async' but is not marked with 'await'"
dismiss(nil) // works
}
实际上,调用dismiss()
应该是可行的,因为编译器应该能够检测到具有该名称的函数的非异步版本。为什么这个不起作用?解决此问题的唯一方法是像上一个示例一样指定nil
吗?
1条答案
按热度按时间cdmah0mi1#
您得到的错误是故意设计的。由于您已将这两个函数命名为相同的名称,因此SWIFT假定这两个方法执行相同的任务,并根据调用者的上下文选择实际的方法。
因为您的
myFunc
函数是异步的,所以SWIFT优先选择dismiss
的异步版本,如果您将myFunc
设置为同步的dismiss
,则优先选择带有完成处理程序的dismiss
。尽管,在我看来,这应该是一个警告,而不是一个错误。现在假设您的同步
dismiss
函数执行一些不应该在MainActor
上执行的长计算。现在,例如,如果您的当前代码被编译器接受,它将在运行时导致您的应用程序卡顿。SWIFT在此指示选择异步dismiss
,这样您的复杂工作将在后台运行,从而释放MainActor
来处理其他任务。