PyQt6实例_批量下载pdf工具_主线程启用线程池

目录

前置:

代码:

视频:


前置:

1 本系列将以 "PyQt6实例_批量下载pdf工具"开头,放在 【PyQt6实例】 专栏

2 本系列涉及到的PyQt6知识点:

线程池:QThreadPool,QRunnable;

信号与槽:pyqtSignal,pyqtSlot;

界面:QTextEdit,QLabel,QLineText,QPushButton,QMainWindow,QWidget;

布局:QHBoxLayout,QVBoxLayout;

弹框:QFileDialog,QMessageBox。

3 本系列后续会在B站录制视频,到时会在文末贴出链接。本人还是建议先看博文,不懂的再看视频,这样效率高,节约时间。

代码:

复制代码
    def execute_btn_clicked(self):
        txt_dir = self.txtdir_lineedit.text()
        if txt_dir is None or len(txt_dir.strip())<=0:
            self.information_dialog('请先选择txt所在目录')
            return
        txt_list = os.listdir(txt_dir)
        if len(txt_list)<=0:
            self.information_dialog('txt所在目录为空')
            return
        pdf_dir = self.savedir_lineedit.text()
        if pdf_dir is None or len(pdf_dir.strip())<=0:
            self.information_dialog('请设置pdf存储目录')
            return
        answer = QMessageBox.question(
            self,
            '确认启动?',
            f'如果确定启动,程序将把任务分成 {self.max_thread_count} 个线程执行。执行过程将占用设备资源。',
            QMessageBox.StandardButton.Yes | QMessageBox.StandardButton.No
        )
        if answer == QMessageBox.StandardButton.Yes:
            self.this_time_start_yeah = True
            self.thread_finished_count = 0
            self.txtdir_lineedit.setDisabled(True)
            self.savedir_lineedit.setDisabled(True)
            self.choicedir_btn.setDisabled(True)
            self.savedir_btn.setDisabled(True)
            self.execute_btn.setDisabled(True)
            if self.last_time_executed_tickers is not None:
                for one in self.last_time_executed_tickers:
                    txt_list.remove(f'{one}.txt')
                pass
            # 分发任务
            interval = len(txt_list)//self.max_thread_count
            if interval == 0:
                self.max_thread_count = 1
                self.insert_executelog('需要执行的内容很少,只开启一个线程')
                pass
            for i in range(0,self.max_thread_count):
                if i == self.max_thread_count-1:
                    node_txt_list = txt_list[i*interval:]
                else:
                    node_txt_list = txt_list[i*interval:(i+1)*interval]
                task_data = {
                    'txt_dir':txt_dir,
                    'pdf_dir':pdf_dir,
                    'txt_list':node_txt_list,
                    'temp_dict':self.last_time_data
                }
                worker = Worker(i,task_data)
                worker.signals.result.connect(self.thread_result_fn)
                worker.signals.finished.connect(self.thread_finished_fn)
                worker.signals.error.connect(self.thread_error_fn)
                self.runner_list.append(worker)
                self.insert_otherlog(f'线程 {i} 启动。')
                self.threadpool.start(worker)
            pass
        else:
            return
        pass
    def thread_result_fn(self,res:tuple):
        # (thread_num,stoped,ticker,executed_url_list,excuted_ticker_list)
        # (thread_num,success,None,None,excuted_ticker_list)
        thread_num = res[0]
        status = res[1]
        if status == 'stoped':
            self.insert_otherlog(f'线程 {thread_num} 停止.')
            if res[2] is not None:
                self.pre_last_time_data[res[2]] = res[3]
            self.pre_last_time_executed_tickers.extend(res[4])
            pass
        else:
            self.insert_otherlog(f'线程 {thread_num} 正常结束。')
        pass
    def thread_finished_fn(self,res:int):
        self.thread_finished_count += 1
        res_str = f'线程 {res} 结束.'
        self.insert_otherlog(res_str)
        if self.thread_finished_count == self.max_thread_count:
            temp_str = '上次执行正常结束'
            if self.pre_last_time_data:
                temp_str = '上次被强制停止'
                with open(os.path.join(basedir,'data','temp.json'),'w',encoding='utf-8') as fw:
                    json.dump(self.pre_last_time_data,fw)
                pass
            if len(self.pre_last_time_executed_tickers)>0:
                temp_str = '上次被强制停止'
                tickers_str = '\n'.join(self.pre_last_time_executed_tickers)
                with open(os.path.join(basedir,'data','executed.txt'),'w',encoding='utf-8') as fw:
                    fw.write(tickers_str)
                pass
            pre_str = f"{self.txtdir_lineedit.text()};{self.savedir_lineedit.text()};{temp_str}"
            with open(os.path.join(basedir,'data','params.txt'),'w',encoding='utf-8') as fw:
                fw.write(pre_str)
            if self.waitting_close:
                self.close()
            else:
                self.txtdir_lineedit.setDisabled(False)
                self.savedir_lineedit.setDisabled(False)
                self.choicedir_btn.setDisabled(False)
                self.savedir_btn.setDisabled(False)
                self.execute_btn.setDisabled(False)
                self.infomation_dialog('所有工作线程停止完毕')
            pass
        pass
    def thread_error_fn(self,res:tuple):
        error_str = f"线程 {res[0]} 报错。报错类型:{res[1]}。值:{res[2]}。异常栈:{res[3]}"
        self.insert_executelog(error_str)
        pass

视频:

https://www.bilibili.com/video/BV1zeZcYQEax/

https://www.bilibili.com/video/BV1BeZcYQEZq/

https://www.bilibili.com/video/BV1VSZAYJEUf/

https://www.bilibili.com/video/BV1KKZPYBEJV/

https://www.bilibili.com/video/BV1KKZPYBEG2/

相关推荐
程序猿与金融与科技1 天前
PyQt6实例_批量下载pdf工具_exe使用方法
pyqt6
程序猿与金融与科技3 天前
PyQt6实例_批量下载pdf工具_线程池
pyqt6
冷心笑看丽美人4 个月前
实现点名神器的pyqt6实现
python·pyqt·pyqt6
ziyu_jia7 个月前
Python教程(二十) : 十分钟入门【PyQt6】
python·pyqt·pyqt6
岳涛@心馨电脑8 个月前
Win/Mac/Linux/Andriod/IOS界面UI设计 - pyside6 - 03 文件(JSON/TXT/PD)查看和打印
前端·python·pyqt6·pyside6
冷心笑看丽美人8 个月前
入门 PyQt6 看过来(案例)13~ 制作一个颜色调节器
开发语言·python·qt·pyqt·pyqt6·python知识
乙酸氧铍9 个月前
【Pyqt6 学习笔记】实现串口调试助手,并将接收到数据模拟键盘输出
笔记·学习·ui·pyqt·gui·pyqt6·pyqt5
乙酸氧铍10 个月前
【Pyqt6 学习笔记】DIY一个二维码解析生成小工具
python·ui·pyqt·pyqt6·pyqt5
老狼IT工作室1 年前
[Python] pyqt6+opencv实现摄像头图像的实时读取并显示(完整源代码)
python·opencv·pyqt6