簡體   English   中英

Swift - async/await - 在 MainActor 任務的后台線程上執行異步方法

[英]Swift - async/await - Execute async method on background thread from MainActor Task

這是我的viewDidLoad方法:

func viewDidLoad() {
    // Stuff here
    Task { @MainActor in 
        doSomeWorkOnMainThread1()
        doSomeWorkOnMainThread2()

        await doSomeBackgroundWork()

        doSomeWorkOnMainThread3()
        doSomeWorkOnMainThread4()
    }
}

這是我應該在后台線程上執行工作的方法:

func doSomeBackgroundWork() async {
    // can add some code here
    // long image processing task
    assert(!Thread.isMainThread)
    // can add some code here
}

是否可以在后台線程上執行doSomeBackgroundWork (不使用 GCD),並在返回主線程之前等待它?

您正在尋找 Task.sleep。 請注意,它以納秒為單位,這真的很奇怪,所以我寫了一個擴展來切換到秒; 要獲得它,您必須使用 Double,而不是 Int:

extension Task where Success == Never, Failure == Never {
    static func sleep(_ seconds:Double) async {
        await self.sleep(UInt64(seconds * 1_000_000_000))
    }
    static func sleepThrowing(_ seconds:Double) async throws {
        try await self.sleep(nanoseconds: UInt64(seconds * 1_000_000_000))
    }
}

保證在后台線程上完成一項工作的方法是將這項工作交給一個 Actor。 這就是 Actor 的用途(部分)。

例如,如果一個 Actor 有一個調用Task.sleep的方法doSleep ,那么如果您實例化該 Actor 並從您的 Task 調用該方法,它將在后台線程上休眠。

該解決方案有效,但我猜它並不完美:

func doSomeBackgroundWork() async {
    await Task {
        // long image processing task
        assert(!Thread.isMainThread)
    }.result
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM