Python 线程处理 - join() - 多线程

Posted

技术标签:

【中文标题】Python 线程处理 - join() - 多线程【英文标题】:Python threads handling - join() - Multithreading 【发布时间】:2018-09-12 13:42:18 【问题描述】:

我正在编写一个脚本,其中执行简单任务的线程每 3 分钟启动一次。我正在使用 threadingschedule 模块。

由于多线程的性质,线程使用相同的资源。

我需要实现什么?

创建新线程时,我想检查是否有任何正在运行的线程;如果有,则等到正在运行的线程终止,然后启动新线程。

我尝试了什么?

 import threading

def run_threaded(job_fn):
    job_thread = threading.Thread(target=job_fn)
    bot.logger.info(" --------------No of active threads : "+threading.activeCount())
    job_thread.start()
    job_thread.join()
    bot.logger.info(" --------------No of active threads : " + threading.activeCount())


schedule.every(3).minutes.do(run_threaded, job)


while True:
    schedule.run_pending()

注意:在上面的示例中,每个 job_thread 需要 5 分钟才能完成。因此它每 6 分钟创建 1 个线程。

据我了解,job_thread.join() 行正在加入主线程(与任何其他活动线程)。尽管调度被阻塞,因此在前一个线程完成之前不能实例化任何其他线程。那是对的吗 ?如果是的话,这是一个很好的做法吗?

为了记录..脚本可以在运行线程时执行其他代码块吗?或者它可以在前一个线程完成之前实例化其他线程,如果他们要执行另一个作业,比如说 job2

【问题讨论】:

是的。您可以在前一个线程完成之前实例化其他线程。事实上,这才是重点:如果你的主线程在每次schedule 运行中所做的只是:(1)启动工作线程,(2)等待工作线程结束,那么创建一个工作就没有意义了线程。你可以在你的主线程中做同样的工作。多线程的优点是不同的线程可以同时执行。如果您不想/不需要同时执行多项操作,则无需使用多线程。 好的,谢谢。出于好奇,你能给我一个同时实例化两个线程的示例代码吗?我如何检查其中哪些已完成,哪些仍在运行? 【参考方案1】:

这是一个简单的示例,显示了多个线程正在启​​动,每个线程将在不同的时间自行终止,以及主线程如何确定每个线程何时终止。

#!/usr/bin/env python3
import threading
import time
import queue

class Worker(threading.Thread):
    def __init__(self, duration, tqueue):
        self.duration = duration
        self.tqueue = tqueue
        super().__init__()
    def run(self):
        # Do real work here instead of just sleeping
        time.sleep(self.duration)
        # Tell parent we are gone by putting our instance to the queue
        self.tqueue.put(self)

def main():
    thr_duration = [2.0, 1.5, 0.5, 2.7, 1.25]
    workers = []
    thr_queue = queue.Queue()

    # Start all threads
    for dur in thr_duration:
        worker = Worker(dur, thr_queue)
        worker.start()
        workers.append(worker)
        print("Started thread , duration ".format(worker.name, dur))

    # Wait for all threads to terminate
    while workers:
        worker = thr_queue.get()
        worker.join()
        print("Reaped thread ".format(worker.name))
        workers.remove(worker)

if __name__ == '__main__':
    main()

【讨论】:

以上是关于Python 线程处理 - join() - 多线程的主要内容,如果未能解决你的问题,请参考以下文章

Python 多进程多线程效率比较

Python 多线程效率不高吗

线程概念及多线程控制

Python threading 中join()的作用

案例_(多线线程)爬取糗事百科

通过网络图片小爬虫对比Python中单线程与多线(进)程的效率