简体   繁体   English

python退出阻塞线程?

[英]python exit a blocking thread?

In my code I loop though raw_input() to see if the user has requested to quit. 在我的代码中,我循环通过raw_input()来查看用户是否已请求退出。 My app can quit before the user quits, but my problem is the app is still alive until I enter a key to return from the blocking function raw_input() . 我的应用程序可以在用户退出之前退出,但我的问题是应用程序仍处于活动状态,直到我输入一个键从阻塞函数raw_input() Can I do to force raw_input() to return by maybe sending it a fake input? 我可以通过发送假输入来强制raw_input()返回吗? Could I terminate the thread that it's on? 我可以终止它所在的线程吗? (the only data it has is a single variable called wantQuit ). (它拥有的唯一数据是一个名为wantQuit变量)。

Why don't you just mark the thread as daemonic? 你为什么不把线程标记为守护进程?

From the docs : 来自文档

A thread can be flagged as a “daemon thread”. 线程可以标记为“守护程序线程”。 The significance of this flag is that the entire Python program exits when only daemon threads are left. 这个标志的意义在于,当只剩下守护进程线程时,整个Python程序都会退出。 The initial value is inherited from the creating thread. 初始值继承自创建线程。 The flag can be set through the daemon attribute. 可以通过守护程序属性设置标志。

You might use a non-blocking function to read user input. 您可以使用非阻塞功能来读取用户输入。
This solution is windows-specific: 此解决方案是特定于Windows的:

import msvcrt
import time

while True:
    # test if there are keypresses in the input buffer
    while msvcrt.kbhit(): 
        # read a character
        print msvcrt.getch()
    # no keypresses, sleep for a while...
    time.sleep(1)

To do something similar in Unix, which reads a line at a time, unlike the windows version reading char by char (thanks to Aaron Digulla for providing the link to the python user forum): 要在Unix中做类似的事情,它一次读取一行,不像windows版本通过char读取char(感谢Aaron Digulla提供了python用户论坛的链接):

import sys
import select

i = 0
while i < 10:
    i = i + 1
    r,w,x = select.select([sys.stdin.fileno()],[],[],2)
    if len(r) != 0:
        print sys.stdin.readline()

See also: http://code.activestate.com/recipes/134892/ 另见: http//code.activestate.com/recipes/134892/

You can use this time out function that wraps your function. 你可以使用这个包装你的功能的超时功能。 Here's the recipe from: http://code.activestate.com/recipes/473878/ 这里的食谱来自: http//code.activestate.com/recipes/473878/

def timeout(func, args=(), kwargs={}, timeout_duration=1, default=None):
    '''This function will spwan a thread and run the given function using the args, kwargs and 
    return the given default value if the timeout_duration is exceeded 
    ''' 
    import threading
    class InterruptableThread(threading.Thread):
        def __init__(self):
            threading.Thread.__init__(self)
            self.result = default
        def run(self):
            try:
                self.result = func(*args, **kwargs)
            except:
                self.result = default
    it = InterruptableThread()
    it.start()
    it.join(timeout_duration)
    if it.isAlive():
        return it.result
    else:
        return it.result

There is a post on the Python mailing list which explains how to do this for Unix: Python邮件列表上有一篇文章解释了如何在Unix上执行此操作:

# this works on some platforms:

import signal, sys

def alarm_handler(*args):
    raise Exception("timeout")

def function_xyz(prompt, timeout):
    signal.signal(signal.SIGALRM, alarm_handler)
    signal.alarm(timeout)
    sys.stdout.write(prompt)
    sys.stdout.flush()
    try:
        text = sys.stdin.readline()
    except:
        text = ""
    signal.alarm(0)
    return text

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM