使用Python 3和Windows 7进行定时输入 [英] Timed input with Python 3 and Windows 7
问题描述
我正在寻找一种解决方案,以便在一定时间后使用户的输入超时.此代码应在5秒钟后显示成功...",而无需用户进行任何交互:
I'm looking for a solution to time out a user's input after a certain time. This code should print "success..." after 5 seconds without any interaction from the user:
def input_with_timeout(timeout):
print ("Hello, you can type and press enter to change 'ans' variable value or wait "+str(timeout)+" seconds and the program will continue")
ans=input() #pass input after timeout
return ans
s="mustnotchange"
s=input_with_timeout(5)
if s=="mustnotchange":
print("Success, if you didn't just cheat by writing mustnotchange")
else:
print("you answered : "+s+" variable value has changed")
我知道这个问题经常被问到,但是以下主题中提供的NONE解决方案适用于WINDOWS 7和Python 3(Windows 7最终" SP1 64位和Python 3.6.8 64位) Python 3定时输入
I know this question was asked often, but NONE solutions provided in the following topics work on WINDOWS 7 and Python 3 (windows 7 "ultimate" SP1 64 bits and Python 3.6.8 64 bits) Python 3 Timed Input
实际上,我正在使用技巧"来避免此问题:我使用os.startfile()启动了另一个python脚本,但是启动时它无法对输入做出反应.
Actually I'm using a "trick" to avoid this problem : I launch another python script with os.startfile() but it can't react to input when started.
如果没有任何可行的答案,做到这一点一定很困难(多处理,线程,队列...),但这在很多情况下肯定会有所帮助.
It must be very difficult to do it (multiprocessing, threading, queues...) if there isn't any working answers about it, but this can certainly help in a lot of situations.
谢谢.
推荐答案
最后,我修改了 @Darkonaut的答案(谢谢!)以匹配我的第一种情况,并在其中添加了模拟键盘"库 pynput
自动按"Enter"键.
Finally I modified @Darkonaut answer (Thank you!) to match my first situation and I added a "simulated keyboard" with the library pynput
to automatically press "Enter".
请注意,这在终端机(Python 3.6.8和Windows 7 SP1)中有效,但是如果从IDLE开始,则不起作用.
Note that this works in Terminal (Python 3.6.8 and Windows 7 SP1) but DOESN'T WORK IF STARTED WITH IDLE.
from threading import Thread, enumerate, Event
from queue import Queue, Empty
import time
from pynput.keyboard import Key, Controller
SENTINEL = None
class PromptManager(Thread):
def __init__(self, timeout):
super().__init__()
self.timeout = timeout
self._in_queue = Queue()
self._out_queue = Queue()
self.prompter = Thread(target=self._prompter, daemon=True)
self._prompter_exit = Event()
def run(self):
"""Run worker-thread. Start prompt-thread, fetch passed
input from in_queue and forward it to `._poll()` in MainThread.
If timeout occurs before user-input, enqueue SENTINEL to
unblock `.get()` in `._poll()`.
"""
self.prompter.start()
try:
txt = self._in_queue.get(timeout=self.timeout)
except Empty:
self._out_queue.put(SENTINEL)
print(f"\n[{time.ctime()}] Please press Enter to continue.")
# without usage of _prompter_exit() and Enter, the
# prompt-thread would stay alive until the whole program ends
keyboard = Controller()
keyboard.press(Key.enter)
keyboard.release(Key.enter)
self._prompter_exit.wait()
else:
self._out_queue.put(txt)
def start(self):
"""Start manager-thread."""
super().start()
return self._poll()
def _prompter(self):
"""Prompting target function for execution in prompter-thread."""
self._in_queue.put(input(f"[{time.ctime()}] >$ "))
self._prompter_exit.set()
def _poll(self):
"""Get forwarded inputs from the manager-thread executing `run()`
and process them in the parent-thread.
"""
msg = self._out_queue.get()
self.join()
return msg
def input_with_timeout(default, timeout):
print ("Hello, you can type and press enter to change 'ans' variable value or wait "+str(timeout)+" seconds and the program will continue")
pm = PromptManager(timeout)
ans= pm.start()
if isinstance(ans, str):
print("ok")
return ans
else:
return default
s="mustnotchange"
s=input_with_timeout(s,5)
if s=="mustnotchange":
print("Success, if you didn't just cheat by writing mustnotchange")
else:
print("you answered : "+s+" variable value has changed")
time.sleep(5)
这篇关于使用Python 3和Windows 7进行定时输入的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!