如何解决Swift:如何将工作人员放入单独的线程中,在主视图中显示结果?
我想知道是否有一种简单的方法可以做到这一点:将长时间运行的工作线程放入单独的线程中,以免阻塞 UI。并在主视图中显示结果。在 SwiftUI 或 UIKit 下。我在网上找到的都是非常复杂的。还是 Swift 中有完全不同的方法?
我制作了一个简约的 Python 程序来展示我想要做什么。在 MacOS 中显示 WiFi 信号强度。
import time
import sys
import subprocess
from PyQt5.QtWidgets import QApplication,QWidget,QLabel,QHBoxLayout
from PyQt5.QtCore import QObject,pyqtSignal,QThread
class Worker(QObject):
send_output = pyqtSignal(str)
def __init__(self):
super().__init__()
def worker(self):
while True:
_out = subprocess.check_output(
["/System/Library/PrivateFrameworks/Apple80211.framework/Versions/Current/Resources/airport","-I"])\
.decode("utf-8")
self.send_output.emit("RSSI: " + _out.splitlines()[0][-3:] + " dBm")
time.sleep(2)
class MainWindow(QWidget):
do_work = pyqtSignal(object)
def __init__(self):
super().__init__()
self.label = QLabel()
layout = QHBoxLayout()
self.setLayout(layout)
layout.addWidget(self.label)
self.show()
self.app_thread = QThread()
self.app = Worker()
self.app.moveToThread(self.app_thread)
self.app.send_output.connect(self.output_label)
self.app_thread.started.connect(self.app.worker)
self.app_thread.start()
def output_label(self,_str):
self.label.setText(_str)
if __name__ == '__main__':
application = QApplication(sys.argv)
mainwindow = MainWindow()
sys.exit(application.exec())
我现在正在努力寻找进入 Swift 的方法。这很令人兴奋,但确实是一件大事。提前致谢!
解决方法
这是一个非常宽泛的问题,所以我也将回答这个问题。
是的,您可以在单独的线程中运行任务,然后将数据返回到主线程。有很多方法可以做到这一点,一种常见的方法是 DispatchQueue
。
让我们举一个过于简化的例子(绝对不是真实世界的代码):
struct ContentView : View {
@State var result = ""
var body: some View {
Text("Result: \(result)")
.onAppear {
DispatchQueue.global(qos: .background).async {
//do your long-running code
var innerResult = 0
for i in 0...1000000 {
innerResult += 5
print(i)
//use DispatchQueue.main.async here if you want to update during the task
}
//update at the end:
DispatchQueue.main.async {
result = "Done! \(innerResult)"
}
}
}
}
}
在这个例子中,当视图出现时,一个任务在后台线程中运行,通过 DispatchQueue
。在这种情况下,我只是利用这样一个事实,即打印到控制台是一项相当昂贵的操作,如果执行一百万次。
当它完成时,它会分派回主线程并更新状态变量中的结果。
DispatchQueue
并非特定于 UIKit 或 SwiftUI —— 使用 SwiftUI 将演示放在一起是最简单的。
如果您要真正开始编写代码来执行此操作,您需要对 DispatchQueues 的工作方式进行一些研究,包括使用哪个队列、是否创建自己的队列、是否希望按顺序完成任务等,但对于这是否可以完成(以及如何容易)的广泛问题,这至少显示了基础知识。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。