控制线程的正确方法是什么?

时间:2018-10-10 23:02:24

标签: python multithreading thread-safety

我大约需要运行3或5个线程,该线程监视OS中的某些活动。因此,主程序必须在后台运行。我已经阅读了许多示例和说明,但是还不清楚如何在后台启动线程和主程序,然后再控制它们。

我从主程序以守护程序模式启动线程:

import threading
import time

def fun1():
    while True:
        print("Thread 1")
        time.sleep(1)

def fun2():
    while True:
        print("Thread 2")
        time.sleep(1)

def fun3():
    while True:
        print("Thread 3")
        time.sleep(1)

def main():
    thread1 = threading.Thread(target=fun1)
    thread1.daemon = True
    thread1.start()

    thread2 = threading.Thread(target=fun2)
    thread2.daemon = True
    thread2.start()

    thread3 = threading.Thread(target=fun3)
    thread3.daemon = True
    thread3.start()

if __name__ == '__main__':
    try:
        main()
        while True:
            print("------------")
            print("Main program")
            print("------------")
            time.sleep(3)
    except (KeyboardInterrupt, SystemExit):
        print("Terminated")

之后,我在后台运行main程序(我不确定这是否是实现我想要实现的最佳方法):

python daemon_thread.py &

如果需要停止特定线程,更改其状态或执行其他操作,如何在主程序初始化之后控制线程?如何访问特定线程或主程序?

1 个答案:

答案 0 :(得分:0)

我现在了解如何解决该问题:我有一个在后台运行的主程序,该主程序有一些线程。但是我想用另一个脚本或程序安全地停止线程的主程序,并在某些情况下暂停并恢复线程。

我对如何使用线程没有正确的概念。我可以使用数据库或配置文件从主程序How?停止或向该线程发送信号。

我通过以下更改更新了项目:

import threading
import time
import sqlite3

def fun1(stop_event1):
    while not stop_event1.is_set(): 
        print("Thread 1")
        time.sleep(1)

def fun2(stop_event2):
    while not stop_event2.is_set(): 
        print("Thread 2")
        time.sleep(1)

def fun3(stop_event3):
    while not stop_event3.is_set(): 
        print("Thread 3")
        time.sleep(1)

def main():
    stop_event1 = threading.Event()
    thread1 = threading.Thread(target=fun1, args=(stop_event1,))
    thread1.daemon = True
    thread1.start()

    stop_event2 = threading.Event()
    thread2 = threading.Thread(target=fun2, args=(stop_event2,))
    thread2.daemon = True
    thread2.start()

    stop_event3 = threading.Event()
    thread3 = threading.Thread(target=fun3, args=(stop_event3,))
    thread3.daemon = True
    thread3.start()

    while True:
        print("------------")
        print("Main program")
        print("------------")
        time.sleep(3)            
        if alive_main():
            print("Finish Threads")
            stop_event1.set()
            stop_event2.set()
            stop_event3.set()

            print("Bye")
            break


def alive_main():
    conn = sqlite3.connect('example.db')
    c = conn.cursor()
    c.execute('SELECT alive_main FROM config')
    row = c.fetchone()
    if row[0] == 1:
        return True
    else:
        return False

if __name__ == '__main__':
    try:
        main()
    except (KeyboardInterrupt, SystemExit):
        print("Terminated")

如果我想更改另一个类或脚本的线程状态,只需更改数据库中的配置表,即可在Threads中从主函数生效。在此示例中,如果我正确停止线程并进行编程,仅更新表即可。

sqlite> UPDATE config SET alive_main = 1;

我需要阅读有关SignalsCondition Objects的内容,以正确补充线程的使用。

谢谢大家!