如何设置RAW_INPUT [重复]的时间限制
-
05-10-2019 - |
题
这个问题在这里已经有一个答案:
- 函数调用超时 14个答案
在Python中,是否有一种方法可以在等待用户输入时计算时间,以便在30秒之后, raw_input()
功能会自动跳过?
解决方案
这 信号 不幸的是, @jer推荐解决方案所基于的 @jer推荐解决方案的功能仅是Unix。如果您需要跨平台或特定于Windows的解决方案,则可以基于 螺纹 而是使用 thread.interrupt_main 发送 KeyboardInterrupt
从计时器线程到主线程。 IE:
import thread
import threading
def raw_input_with_timeout(prompt, timeout=30.0):
print prompt,
timer = threading.Timer(timeout, thread.interrupt_main)
astring = None
try:
timer.start()
astring = raw_input(prompt)
except KeyboardInterrupt:
pass
timer.cancel()
return astring
无论是30秒的时间外还是用户明确决定击中Control-C以放弃输入任何内容,但似乎可以返回,但似乎可以以相同的方式处理这两种情况(如果您需要区分,可以使用,可以使用对于计时器,您自己的函数,在中断主线程之前,记录了超时的事实 有 发生了,在您的处理程序中 KeyboardInterrupt
访问“某个地方”以区分两种情况中的哪一个)。
编辑: :我本可以发誓这是有效的,但我一定是错误的 - 上面的代码省略了明显需要的 timer.start()
, 和 即使有了它,我也不能再起作用了。 select.select
显然可以尝试的另一件事,但它不会在Windows中的“正常文件”(包括stdin)上使用 - 在Unix中,它在所有文件,Windows,仅在插座上都可以使用。
因此,我不知道如何进行跨平台“与超时”进行“原始输入”。特定于Windows的循环轮询可以构建 msvcrt.kbhit, ,执行 msvcrt.getche
(并检查是否是指示输出完成的返回,在这种情况下,它会从循环中漏出,否则会累积并继续等待)并在需要时检查时间。我无法测试,因为我没有Windows机器(它们都是Mac和Linux),但是这里是 未经测试的代码 我会建议:
import msvcrt
import time
def raw_input_with_timeout(prompt, timeout=30.0):
print prompt,
finishat = time.time() + timeout
result = []
while True:
if msvcrt.kbhit():
result.append(msvcrt.getche())
if result[-1] == '\r': # or \n, whatever Win returns;-)
return ''.join(result)
time.sleep(0.1) # just to yield to other processes/threads
else:
if time.time() > finishat:
return None
OP在评论中说他不想 return None
超时,但是还有什么选择?提出例外?返回其他默认值?无论他想要什么选择,他都可以清楚地将其代替我 return None
;-).
如果您不想只是因为用户输入而止步 慢慢地 (与完全不打字相反! - ),您可以在每个成功的角色输入后重新计算完成。
其他提示
我找到了解决这个问题的解决方案 在博客文章中. 。这是该博客文章的代码:
import signal
class AlarmException(Exception):
pass
def alarmHandler(signum, frame):
raise AlarmException
def nonBlockingRawInput(prompt='', timeout=20):
signal.signal(signal.SIGALRM, alarmHandler)
signal.alarm(timeout)
try:
text = raw_input(prompt)
signal.alarm(0)
return text
except AlarmException:
print '\nPrompt timeout. Continuing...'
signal.signal(signal.SIGALRM, signal.SIG_IGN)
return ''
请注意: 此代码只能在 *nix oss上使用.
from threading import Timer
def input_with_timeout(x):
def time_up():
answer= None
print 'time up...'
t = Timer(x,time_up) # x is amount of time in seconds
t.start()
try:
answer = input("enter answer : ")
except Exception:
print 'pass\n'
answer = None
if answer != True: # it means if variable have somthing
t.cancel() # time_up will not execute(so, no skip)
input_with_timeout(5) # try this for five seconds
由于它是自定义的...在命令行提示中运行它,希望您能得到答案 Python Doc 您将很清楚此代码中刚刚发生的事情!
Input()函数旨在等待用户输入某物(至少[Enter]键)。
如果您未用来使用输入(),则下面是使用TKINTER的更轻的解决方案。在TKINTER中,对话框(和任何小部件)在给定时间后可以被销毁。
这是一个示例:
import tkinter as tk
def W_Input (label='Input dialog box', timeout=5000):
w = tk.Tk()
w.title(label)
W_Input.data=''
wFrame = tk.Frame(w, background="light yellow", padx=20, pady=20)
wFrame.pack()
wEntryBox = tk.Entry(wFrame, background="white", width=100)
wEntryBox.focus_force()
wEntryBox.pack()
def fin():
W_Input.data = str(wEntryBox.get())
w.destroy()
wSubmitButton = tk.Button(w, text='OK', command=fin, default='active')
wSubmitButton.pack()
# --- optionnal extra code in order to have a stroke on "Return" equivalent to a mouse click on the OK button
def fin_R(event): fin()
w.bind("<Return>", fin_R)
# --- END extra code ---
w.after(timeout, w.destroy) # This is the KEY INSTRUCTION that destroys the dialog box after the given timeout in millisecondsd
w.mainloop()
W_Input() # can be called with 2 parameter, the window title (string), and the timeout duration in miliseconds
if W_Input.data : print('\nYou entered this : ', W_Input.data, end=2*'\n')
else : print('\nNothing was entered \n')
诅咒示例,该示例进行定时数学测试
#!/usr/bin/env python3
import curses
import curses.ascii
import time
#stdscr = curses.initscr() - Using curses.wrapper instead
def main(stdscr):
hd = 100 #Timeout in tenths of a second
answer = ''
stdscr.addstr('5+3=') #Your prompt text
s = time.time() #Timing function to show that solution is working properly
while True:
#curses.echo(False)
curses.halfdelay(hd)
start = time.time()
c = stdscr.getch()
if c == curses.ascii.NL: #Enter Press
break
elif c == -1: #Return on timer complete
break
elif c == curses.ascii.DEL: #Backspace key for corrections. Could add additional hooks for cursor movement
answer = answer[:-1]
y, x = curses.getsyx()
stdscr.delch(y, x-1)
elif curses.ascii.isdigit(c): #Filter because I only wanted digits accepted
answer += chr(c)
stdscr.addstr(chr(c))
hd -= int((time.time() - start) * 10) #Sets the new time on getch based on the time already used
stdscr.addstr('\n')
stdscr.addstr('Elapsed Time: %i\n'%(time.time() - s))
stdscr.addstr('This is the answer: %s\n'%answer)
#stdscr.refresh() ##implied with the call to getch
stdscr.addstr('Press any key to exit...')
curses.wrapper(main)
在Linux下,One可以使用诅咒和Getch功能,其非阻止。请参阅getch()
https://docs.python.org/2/library/curses.html
等待键盘输入X秒的功能(您必须先初始化诅咒窗口(Win1)!
import time
def tastaturabfrage():
inittime = int(time.time()) # time now
waitingtime = 2.00 # time to wait in seconds
while inittime+waitingtime>int(time.time()):
key = win1.getch() #check if keyboard entry or screen resize
if key == curses.KEY_RESIZE:
empty()
resize()
key=0
if key == 118:
p(4,'KEY V Pressed')
yourfunction();
if key == 107:
p(4,'KEY K Pressed')
yourfunction();
if key == 99:
p(4,'KEY c Pressed')
yourfunction();
if key == 120:
p(4,'KEY x Pressed')
yourfunction();
else:
yourfunction
key=0