为了账号安全,请及时绑定邮箱和手机立即绑定

Python – 在无缓冲的标准输入上选择

Python – 在无缓冲的标准输入上选择

米琪卡哇伊 2022-10-18 16:14:51
我真的在为 python3 中的缓冲而苦苦挣扎。我正在尝试实现一个简单的收音机。我有一个接收器类。它向用户显示可用的电台。这些电台是动态的,因此它们会出现和消失。Welcome to the radio, select station you want to listen to.> 1) Rock Station  2) Hip Hop Station  3) Country Station所以接收器必须同时等待输入:来自管道(关于新站显示/消失的信息)和来自标准输入(用户可以使用向上和向下箭头来更改站)。此外,当用户使用箭头键更改电台时,我必须一次从标准输入读取一个字符。这就是标准select.select不起作用的原因(它等待用户按 ENTER 键):class _GetchUnix:    def __init__(self):        import tty, sys    def __call__(self):        import sys, tty, termios        fd = sys.stdin.fileno()        old_settings = termios.tcgetattr(fd)        try:            tty.setraw(sys.stdin.fileno())            ch = sys.stdin.read(1)        finally:            termios.tcsetattr(fd, termios.TCSADRAIN, old_settings)        return chself.char_reader = _GetchUnix()[...]def __read_order_from_user(self,):    k = self.char_reader()    # Check for up/down arrow keys.    if k == '\x1b':        k = self.char_reader()        if k != '[':            return        k = self.char_reader()        if k == 'A':            self.__arrow_down()        if k == 'B':            self.__arrow_up()    # And check for enter key.    if k == '\r':        self.menu[self.option].handler()def __update_stations(self,):    [...]def run(self):    self.display()    while True:        rfds, _, _ = select.select([pipe, sys.stdin], [], [])        if pipe in rfds:                self.__update_stations()        if sys.stdin in rfds:            self.__read_order_from_user()我在互联网上找到了如何从标准输入中逐个读取字符:Python 从用户读取单个字符 并且它确实有效,但与select.select.
查看完整描述

1 回答

?
白衣染霜花

TA贡献1796条经验 获得超10个赞

我在此处粘贴来自 VPfB 评论的解决方案:

"raw tty 模式打开到只读取一个字符然后关闭。当 select 处于活动状态时,它被关闭,因为在 select 之后调用了获取一个字符的例程。你应该打开 raw tty在选择循环之前输入,退出循环后恢复 tty 设置。”


查看完整回答
反对 回复 2022-10-18
  • 1 回答
  • 0 关注
  • 115 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信