如何暂停一个线程(python)

时间:2017-08-02 17:16:05

标签: python multithreading qt python-multithreading

上下文: 我正在使用Qt创建者和python中的“行为”文件构建图形界面。我的GUI的测试版本是:

the test GUI

预期的行为: 我正在运行2个不同的线程,它们被引用到具有不同输入参数的相同函数。使用SELECTOR按钮,我可以将值1或2分配给变量(并显示它) 按钮Start thread启用正确的线程(第一次)。 应通过修改全局running变量,通过停止按钮关闭循环。 这是我的代码

# -*- coding: utf-8 -*-

from PyQt4 import QtCore, QtGui, uic
import sys
import threading
import time
import Queue

running = False
first_thread = None
second_thread = None
form_class = uic.loadUiType("simple2.ui")[0]
q = Queue.Queue()
select = 0


def action(string, queue): #function called by threads
    global running
    while(running):
        phrase = string       
        if queue.qsize() < 10:
            queue.put(phrase)
        #else:
        #   print queue.qsize()

class MyWindowClass(QtGui.QMainWindow, form_class):
    def __init__(self, parent=None):
        QtGui.QMainWindow.__init__(self, parent)
        self.setupUi(self)

        #buttons        
        self.startButton.clicked.connect(self.start_clicked)
        self.stopButton.clicked.connect(self.stop_clicked)
        self.selector.clicked.connect(self.sel_click)
        #variables
        self.first = False
        self.second = False
        #queue
        self.timer = QtCore.QTimer(self)
        self.timer.timeout.connect(self.update_phrase)
        self.timer.start(1)

    def start_clicked(self): #start button callback
        global select
        if select > 0:
            global running
            running = True
            print "started"
            if (not self.first) & (select == 1):
                first_thread.start()
                self.first = True
            if (not self.second) & (select == 2):
                second_thread.start()
                self.second = True
            self.startButton.setEnabled(False)
            self.startButton.setText('Starting...')

    def stop_clicked(self): #stop button callback
        global running
        running = False
        print "stopped"
        self.startButton.setEnabled(True)
        self.startButton.setText('Start Thread')

    def sel_click(self): #selector button callback
        global select
        if select < 2:
           select = select + 1
        else:
            select = 1
        self.thread_counter.setText(str(select))

    def update_phrase(self): #looping function
        global running
        if (not q.empty()) & running:
            self.startButton.setText('Thread on')
            abc = q.get()
            print abc


    def closeEvent(self, event):
        global running
        running = False

if __name__ == "__main__":
    first_thread = threading.Thread(target=action, args = ("first", q))
    second_thread = threading.Thread(target=action, args = ("second", q))
    app = QtGui.QApplication(sys.argv)
    w = MyWindowClass(None)
    w.setWindowTitle('Multiple threads  test in python')
    w.show()
    app.exec_()

现在,每个线程都应该简单地在终端上打印他们的参数(“First”或“Second”)。 如果第一次启动线程,我的代码可以工作。但我想无限次地在线程之间切换。

由于线程无法停止,有没有办法“暂停”它们?

我找不到解决方案,希望有人也会用一段代码帮助我。提前谢谢

1 个答案:

答案 0 :(得分:1)

你可以使用Lock类来做到这一点,一个简单的例子是:

public static IEnumerable<SelectListItem> GetJurisdictions()
    {
        using (var context = new DAL.ObservationEntities())
        {
            List<SelectListItem> JurisdictionsList = new List<SelectListItem>();
            var items = (from j in context.Jurisdictions orderby j.Name select j).ToList();
            foreach (var item in items)
            {
                JurisdictionsList.Add(new SelectListItem() { Text = item.Name.ToString(), Value = item.GUID.ToString() });
            }
            return JurisdictionsList;
        }
    }

然后在另一边做

import threading

lock = threading.Lock()

//here it will be lock 
lock.acquire() # will block if lock is already held
   ... 

你可以在这里阅读更多http://effbot.org/zone/thread-synchronization.htm