gpt4 book ai didi

swift - 如何在后台线程中使用 DispatchGroup?

转载 作者:可可西里 更新时间:2023-11-01 01:07:52 28 4
gpt4 key购买 nike

我有两个函数(或任务),我想一个接一个地运行,我正在使用 DispatchGroup 来跟踪它们并在它们完成时通知我。现在它们正在主线程中完成,但我想在后台线程中运行这些任务。我将如何去做呢?我尝试了几种方法,但它们要么同时运行,要么在第一个方法完成后出现异常错误。下面的代码一个接一个地执行任务,但是如果我在函数内部调用 Thread.current,我可以看到它们正在主线程中运行。

@objc func doWorkFunctions(){
taskGroup.enter()
DispatchQueue.global(qos: .background).sync {
self.firstFunction {
self.taskGroup.leave()
}
}

taskGroup.enter()
DispatchQueue.global(qos: .background).sync {
self.secondFunction {
self.taskGroup.leave()
}
}

taskGroup.notify(queue: .main) {
print("All tasks completed")
}
}

如果我使用以下代码,它们会同时运行但在后台线程中。

@objc func doWorkFunctions(){
taskGroup.enter()
DispatchQueue.global(qos: .background).async {
self.firstFunction {
self.taskGroup.leave()
}
}

taskGroup.enter()
DispatchQueue.global(qos: .background).async {
self.secondFunction {
self.taskGroup.leave()
}
}

taskGroup.notify(queue: .main) {
print("All tasks completed")
}
}

我一直在搜索和搜索,但我似乎无法找到我的问题的答案或对此事的清晰度。有人可以就这里发生的事情提供一些指导。这些是案例中有问题的功能。他们模拟一项长期任务来练习跟踪进度。

func firstFunction(completion: @escaping()->Void){
print(Thread.current)
if childProgressOne.isCancelled { return }
for i in 1...5 {
sleep(1)

childProgressOne.completedUnitCount = Int64(i * 20)

print("Child Progress One: \(childProgressOne.fractionCompleted)")
print("Total Progress: \(totalProgress.fractionCompleted)")
}
completion()
}

func secondFunction(completion: @escaping()->Void){
print(Thread.current)

if childProgressTwo.isCancelled { return }
for i in 1...5 {
sleep(1)

childProgressTwo.completedUnitCount = Int64(i * 20)

print("Child Progress Two: \(childProgressTwo.fractionCompleted)")
print("Total Progress: \(totalProgress.fractionCompleted)")
}
completion()
}

这也按顺序执行它们,但是在函数内部调用 Thread.current 告诉我它们正在主线程中执行,即使它们被调用到后台线程也是如此。

 @objc func doWorkFunctions(){
DispatchQueue.global(qos: .background).sync {
self.taskGroup.enter()
self.firstFunction {
self.taskGroup.leave()
}
self.taskGroup.enter()
self.secondFunction {
self.taskGroup.leave()
}
}

taskGroup.notify(queue: .main) {
print("All tasks completed")
}
}

最佳答案

根据您的描述,我可能根本不会在这里使用调度组。我只是链接这些方法:

@objc func doWorkFunctions() {
DispatchQueue.global(qos: .background).async {
self.firstFunction {
self.secondFunction {
DispatchQueue.main.async {
print("All tasks completed")
}
}
}
}

但是假设你有一个很好的理由在这里建立一个组,你需要做的是使用.notify 来同步它们。 .notify 表示“当组为空时,将此 block 提交到此队列。”

@objc func doWorkFunctions(){
let queue = DispatchQueue.global(qos: .background)

taskGroup.enter()
queue.async {
self.firstFunction {
self.taskGroup.leave()
}
}

taskGroup.notify(queue: queue) {
self.taskGroup.enter()

self.secondFunction {
self.taskGroup.leave()
}

self.taskGroup.notify(queue: .main) {
print("All tasks completed")
}
}
}

(您可能不需要 taskGroup 成为此处的实例属性。您可以将其设为局部变量并减少 self. 所需的引用。每个 block 都有对该组的引用,因此它会一直存在,直到所有 block 都完成。)

关于swift - 如何在后台线程中使用 DispatchGroup?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53972081/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com