0

Qt の QThreadPool を使用したいのですが、QApplication.quit() を呼び出す前にキュー内のワーカーが終了しないと、アプリケーションがハングしているようです。以下の縮小されたテストケースで私が何か間違っているかどうか誰かに教えてもらえますか?

import logging
log = logging.getLogger(__name__)

import sys

from PySide import QtCore

import time

class SomeWork(QtCore.QRunnable):
    def __init__(self, sleepTime=1):
        super(SomeWork, self).__init__()
        self.sleepTime = sleepTime

    def run(self):
        time.sleep(self.sleepTime)
        print "work", QtCore.QThread.currentThreadId()

def _test(argv):
    logging.basicConfig(level=logging.NOTSET)

    app = QtCore.QCoreApplication(argv)

    pool = QtCore.QThreadPool.globalInstance()

    TASK_COUNT = int(argv[1]) if len(argv) > 1 else 1

    mainThread = QtCore.QThread.currentThreadId()
    print "Main thread: %s"%(mainThread)
    print "Max thread count: %s"%(pool.maxThreadCount())
    print "Work count: %s"%(TASK_COUNT)

    for i in range(TASK_COUNT):
        pool.start(SomeWork(1))

    def boom():
        print "boom(); calling app.quit()"
        app.quit()

    QtCore.QTimer.singleShot(2000, boom)

    #import signal
    #signal.signal(signal.SIGINT, signal.SIG_DFL)

    return app.exec_()

if __name__ == '__main__':
    sys.exit(_test(sys.argv))

明確にするために、これは私が得る出力です:

(env)root@localhost:# python test_pool.py 1
Main thread: 3074382624
Max thread count: 1
Work count: 1
work 3061717872
boom(); calling app.quit()

(env)root@workshop:/home/workshop/workshop/workshop# python test_pool.py 20
Main thread: 3074513696
Max thread count: 1
Work count: 20
work 3060783984
boom(); calling app.quit()

そして、最初のコマンドではなく、2 番目のコマンドで永久にハングします。

ご協力いただきありがとうございます。

編集:

  • 明確にするために、スレッドがスレッドキューにある間に app.quit() が呼び出された場合、それらは実行されないことを期待しています。すでに実行中のスレッドは最後まで実行する必要があります。次に、アプリケーションを閉じる必要があります。
  • この例は Windows マシンでも失敗します
  • この例は同じ Windows マシンで動作しますが、PyQt4 を使用しています
4

1 に答える 1

0

exec() の直前にこれを _test() に追加すると、すべてのスレッドが実行されますが、問題が修正されます。

def waitForThreads():
    print "Waiting for thread pool"
    pool.waitForDone()
app.aboutToQuit.connect(waitForThreads)
于 2013-05-06T23:20:12.400 に答える