学习目标:
使用QThread库,创建多线程,可以解决多任务同时工作,避免因顺序任务执行产生的等待延时,
学习内容:
- start()启动线程
- stop()阻止线程
- sleep()强制线程睡眠
学习产出:
`提示:创建线程的 类
class Thread_1(QThread):
def __init__(self):
super().__init__()
def run(self):
values = [1, 2, 3, 4,5]
for i in values:
print(i)
time.sleep(0.5)
class Thread_2(QThread):
def __init__(self):
super().__init__()
def run(self):
values = ['a', 'b', 'c', 'd', 'e']
for i in values:
print(i)
time.sleep(0.5)
def slot_btn1(self):
self.thread_1 = Thread_1()
self.thread_1.start()
def slot_btn2(self):
self.thread_2 = Thread_2()
self.thread_2.start()
·当重复执行其中一个任务时,这种方法,容易造成上一个任务还未结束,新任务就来了。
改进
需要在点击之后开始执行任务,在任务没有结束之前,此任务不允许使用, 有两种方法:
1 添加线程锁
以线程1为例,添加线程锁
qmut_1 = QMutex()
class Thread_1(QThread):
def __init__(self):
super().__init__()
def run(self):
qmut_1.lock()
values = [1, 2, 3, 4,5]
for i in values:
print(i)
time.sleep(0.5)
qmut_1.unlock()
连续执行线程1可以发现,线程1在执行结束后,才开始执行下一个线程1
2 信号
以线程2为例,
class Thread_2(QThread):
_signal =pyqtSignal()
def __init__(self):
super().__init__()
def run(self):
values = ['a', 'b', 'c', 'd', 'e']
for i in values:
print(i)
time.sleep(0.5)
self._signal.emit()
def slot_btn2(self):
self.btn2.setEnabled(False)
self.thread_2 = Thread_2()
self.thread_2._signal.connect(self.set_btn2)
self.thread_2.start()
def set_btn2(self):
self.btn2.setEnabled(True)
执行线程2 可以发现,在线程2结束前,按键是无法操作的;执行结束,才有权限再次执行线程2。
全代码
from cProfile import label
from curses import savetty
from math import e
from PyQt5.QtCore import Qt, QThread, QMutex, pyqtSignal
from PyQt5.QtGui import QPalette
from PyQt5.QtWidgets import (QMainWindow, QApplication, QWidget, QGridLayout, QHBoxLayout,
QToolButton, QPushButton,
QLabel,
QAction, qApp, QMenu,
)
import sys
import time
from pip import main
qmut_1 = QMutex()
class Thread_1(QThread):
def __init__(self):
super().__init__()
def run(self):
qmut_1.lock()
values = [1, 2, 3, 4,5]
for i in values:
print(i)
time.sleep(0.5)
qmut_1.unlock()
class Thread_2(QThread):
_signal =pyqtSignal()
def __init__(self):
super().__init__()
def run(self):
values = ['a', 'b', 'c', 'd', 'e']
for i in values:
print(i)
time.sleep(0.5)
self._signal.emit()
class Thread_3(QThread):
def __init__(self):
super().__init__()
def run(self):
values = ['A', 'B', 'C', 'D', 'E']
for i in values:
print(i)
time.sleep(0.5)
class MainUi(QMainWindow):
def __init__(self):
super().__init__()
self.init_ui()
def init_ui(self):
self.setGeometry(0, 0, 300, 300)
self.setWindowTitle("main")
self.statusBar().showMessage("ok")
new_file = QAction('new file...(&n)',self)
new_file.setShortcut('Ctrl+Q')
new_file.setStatusTip("new file...")
new_file.triggered.connect(qApp.quit)
exit_file = QAction("exit...(&E)", self)
exit_file.setShortcut('Ctrl+E')
exit_file.setStatusTip('Exit...')
max_act = QAction('Max',self)
max_act.triggered.connect(qApp.quit)
save_menu = QMenu("保存方式", self)
save_act = QAction('保存...', self)
save_act.setShortcut('Ctrl+S')
save_act.setStatusTip("'保存...'")
saveas_act = QAction('另存为...(&O)', self)
saveas_act.setStatusTip("文件另存为")
save_menu.addAction(save_act)
save_menu.addAction(saveas_act)
self.menubar = self.menuBar()
file_menu =self.menubar.addMenu("文件")
file_menu.addAction(new_file)
file_menu.addSeparator()
file_menu.addMenu(save_menu)
file_menu.addSeparator()
file_menu.addAction(exit_file)
self.menubar.addMenu(save_menu)
select_menu = self.menubar.addMenu("select")
double_menu =self.menubar.addAction(max_act)
toolbar = self.addToolBar('工具栏')
toolbar.addAction(save_act)
self.main_widget = QWidget()
self.main_layout = QGridLayout()
self.main_widget.setLayout(self.main_layout)
self.left_widget = QWidget()
self.left_widget.setObjectName("left_widget")
self.left_layout = QGridLayout()
self.left_widget.setLayout(self.left_layout)
palette = QPalette()
palette.setColor(QPalette.Background , Qt.white)
self.left_widget.setPalette(palette)
self.left_widget.setAutoFillBackground(True)
self.btn1 = QPushButton("ko1", self)
self.btn1.clicked.connect(self.slot_btn1)
self.btn2 = QPushButton("ko2", self)
self.btn2.clicked.connect(self.slot_btn2)
self.btn3 = QPushButton("ko3", self)
self.btn3.clicked.connect(self.slot_btn3)
self.left_layout.addWidget(self.btn1, 0, 0, 1,1)
self.left_layout.addWidget(self.btn2, 0, 1, 1,1)
self.left_layout.addWidget(self.btn3, 0, 2, 1,1)
self.right_widget = QWidget()
self.right_widget.setObjectName("right_widget")
self.right_layout = QGridLayout()
self.right_widget.setLayout(self.right_layout)
self.main_layout.addWidget(self.left_widget, 0,0, 100,2)
self.main_layout.addWidget(self.right_widget, 0,2, 100,200)
self.setCentralWidget(self.main_widget)
def slot_btn1(self):
self.thread_1 = Thread_1()
self.thread_1.start()
def slot_btn2(self):
self.btn2.setEnabled(False)
self.thread_2 = Thread_2()
self.thread_2._signal.connect(self.set_btn2)
self.thread_2.start()
def set_btn2(self):
self.btn2.setEnabled(True)
def slot_btn3(self):
self.thread_3 = Thread_3()
self.thread_3.start()
if __name__ == '__main__':
app = QApplication(sys.argv)
mainui = MainUi()
mainui.show()
sys.exit(app.exec_())
|