swift 常量推断为具有类型 (),这可能是出乎意料的

Posted

技术标签:

【中文标题】swift 常量推断为具有类型 (),这可能是出乎意料的【英文标题】:swift constant inferred to have type () which may be unexpected 【发布时间】:2021-06-25 22:27:53 【问题描述】:

我有以下代码:

public func test_mutex() async

   let mutex = Mutex()
   async let a = mutex.exclusive("a")  await Tasks.after(ms: 300) print("a")
   async let b = mutex.exclusive("b")  await Tasks.after(ms: 200) print("b")
   async let c = mutex.exclusive("c")  await Tasks.after(ms: 100) print("c")
   _ = await [a, b, c]

我得到了三个这样的错误:

Constant 'a' inferred to have type '()', which may be unexpected

然而 - 重点是我正在测试一个什么都不返回的函数 - 我有另一个测试一个返回一些东西的函数 - 即 () 一点也不意外 - 我不能只做这个返回一些东西。

如何摆脱警告? - 或者我如何以其他方式导致三个异步事件并行发生,然后等待它们。

【问题讨论】:

【参考方案1】:

否则我如何导致三个异步事件并行发生然后等待它们

您使用任务组,如结构化并发视频中所述。

https://developer.apple.com/documentation/swift/3814991-withtaskgroup?changes=__1

对组的async 方法的每次调用都是您调用异步方法以并行运行的机会。当所有调用完成后,任务上的await 完成,我们继续。

或者,我想您可以按照 FixIt 的建议将 a、b 和 c 的类型声明为 ()。但这似乎是一种相当便宜的方法。最好正确地执行此操作。

例如,我编造了一个行为,就像我想象的 Mutex 可能行为一样:

class Waiter 
    func go(after:TimeInterval,  f: @escaping ()->()) async 
        await withUnsafeContinuation  (c:UnsafeContinuation<Void,Never>) in
            DispatchQueue.global().asyncAfter(deadline:.now()+after) 
                f()
                c.resume()
            
        
    

然后编译并运行良好:

    let w = Waiter()
    async let x:() = w.go(after: 1)  print(1) 
    async let y:() = w.go(after: 1)  print(2) 
    async let z:() = w.go(after: 1)  print(3) 
    let _ = [await x, await y, await z]

不过,我还是觉得任务组更好。

    let w = Waiter()
    print("start")
    await withTaskGroup(of:Void.self)  group in
        for i in [1,2,3] 
            group.async 
                await w.go(after:1)  print(i) 
            
        
    
    print("done")

【讨论】:

对不起 - 我可能很愚蠢 - 但我看不出在这种情况下如何使用任务组?至于宣布它们全部无效-尝试过-但它并没有使警告消失:( 哦,好吧,给我一些时间,我给你写代码。我正在下载下一个测试版,所以我需要一段时间才能完成。 — 但是,实际上,我不确定互斥锁是什么,所以这可能更棘手。我的回答仅基于您问的一句话:要请求并行执行,请使用任务组。 你能提供互斥代码吗?否则我想我可以编造一些东西。 您尝试过 Fix-It 吗? 没有修复它 - 但你给了我真正的解决方案 - 这只是 async let a: () = 不管我试过什么 async let a: Void = 不管什么谢谢。这是在测试中 - 所以我认为这比与任务组关联的所有代码要干净得多。

以上是关于swift 常量推断为具有类型 (),这可能是出乎意料的的主要内容,如果未能解决你的问题,请参考以下文章

变量“offerCardsShuffled”推断为“()”类型,这可能是意外的

Swift CoreLocation

Swift 显式与推断类型:性能

深入kotlin - 基础语法

深入kotlin - 基础语法

swift语法100