input vs. readline

cs at zip.com.au cs at zip.com.au
Fri Jul 8 19:45:12 EDT 2016


On 08Jul2016 16:17, John Nagle <nagle at animats.com> wrote:
>   If "readline" is imported, "input" gets "readline" capabilities.
>It also loses the ability to import control characters.  It doesn't
>matter where "readline" is imported; an import in some library
>module can trigger this.  You can try this with a simple test
>case:
>   print(repr(input()))
>as a .py file, run in a console.  Try typing "aaaESCbbb".
>On Windows 7, output is "bbb".  On Linux, it's "aaa\x1bbbb".
>
>So it looks like "readline" is implicitly imported on Windows.

_Or_ that the Windows console app does its own input processing. I would be 
_very_ surprised if Python were behaving differently on the two platforms in 
this regard, though it is possible. (Disclaimer: I pretty much don't use 
Windows).

Remember that any terminal program does some processing of keystrokes before 
they reach your program, even if that is "no" processing. On a UNIX system this 
is called the "line discipline", and doubtless Windows does something of that 
nature.

On a UNIX system in normal circumstances your terminal's line discipline is in 
"cooked" mode, where various things happen to the raw bytes delivered by the 
terminal emulator. For example, when you press <Return> which sends byte 13, in 
cooked mode, this is converted the a newline (byte 10) for receipt by the 
program. Also in cooked mode, backspace (or DEL, depends, see "stty -a") is 
handled by the line disciple: your program sees the text as it was _after_ you 
did all the backspacing. And so forth.

Perhaps the Windows console is treating ESC specially, apparently as "line 
erase", discarduing any preceeding text. Hence your results.

On a UNIX program the normal thing would be to either to:

- accept this, and use the liternal-next kestroke (usually ^V) to tell it not 
  to the bytes special to the line discipline. So you might type ^V^H to get a 
  literal ^H code in your input and so forth.

- use termios to turn off all the control keystrokes (erase, kill and so forth)

- put the terminal into "raw" mode where keystroke bytes are sent through 
  unchanged (although them you need to hand carriage return yourself, etc)

Perhaps Windows has a "literal-next" keystroke line UNIX does.

>   I have a multi-threaded Python program which recognizes ESC as
>a command to stop something.  This works on Linux, but not on
>Windows.  Apparently something in Windows land pulls in "readline".

Unlikely. See above.

>   What's the best way to get input from the console (not any
>enclosing shell script) that's cross-platform, cross-version
>(Python 2.7, 3.x), and doesn't do "readline" processing?

sys.stdin.readline()

input() is a conveience function, now very low level.

Cheers,
Cameron Simpson <cs at zip.com.au>



More information about the Python-list mailing list