Stop python command interpreter from echoing - python

In Linux, python3, I paste this code at the >>> python command-line...
my_string = "Blackpool rock is magic"
string_split = my_string.split() # creates a list.
# Elements of which are each
# word in the string.
print(f"len of string = {len(my_string)}")
for t in range(len(string_split)):
print(f"string_split[{t}] = {string_split[t]}")
print(f"string_split = {string_split}")
Inbetween the pasted code, I see some output inbetween some coded lines
e.g.
How can I get all my print statement to appear at the end of the code and not be interspersed with the code (even though I can see it being useful for debugging)? - Is there an "code echo off" like feature?
Am I right in thinking after a For loop you need to have a blank line?
When pasting code sometime I need to press enter a couple of time to complete the code. Is there an escape character or something to ensure the program terminates without needing to press enter 1 or two times?

Related

Python unexpectedly stopping while loop after getting input multiple times and printing the input

Okay so I was trying out the Google Kick Start problems for the first time when I came across this problem. For some reason when I enter multiple lines of inputs at the same time and then print in between processing each input it makes the loop run forever until I enter in a new input. Is there a simple explanation for this scenario?
x = int(input())
print('\nx =', x)
for i in range(x):
newInput = input()
print(newInput)
If I put the input as:
3
1
2
3
Then the output is:
x = 3
1
2
and then I have to press 'enter' again to see
3
Why does the program require the 2nd input to get the remaining 3 to print?
Curiously when I use the debugger mode with breakpoints on my IDE this problem disappears (no longer need to press 'enter' again).
Python waits for a newline when you call input(). If you copy paste the input data without a newline at the end it doesn't know that the last line is complete, but the lines before that end in newlines so it does them. Make sure that what you copy paste contains a newline at the end.

What does this mean in Python '\x1b[2K'?

I've just learnt that to clear a line that you printed in Python, do this:
sys.stdout.write('\x1b[2K')
Why is it so complicated? what does that weird code mean? and is there any alternative in print command?
Print does offer "end" option that allows to go back and forth in lines, but no way to clear what you printed. Overwriting via \r doesn't always work especially if the new line is shorter than the old one. You will get traces from the old line, so I need clearing first.
Thanks.
\x1b[2K is what's known as an ANSI terminal control sequence. They are a legacy of the 1970s and still used today (but vastly extended) to control terminal emulators.
\x1b is the ASCII for ESCAPE (literally the ESC key on your keyboard). [2K is the command "erase the current line".
There are many libraries in Python for working with the terminal, such as Urwid. These libraries will hide the inner workings of the terminal from you and give you higher-level constructs to create TUIs.
However, there is a much more efficient way of doing this:
You can use the print() command as usual, and delete the screen using
os.system("cls") # For Windows
or
os.system("clear") # For Linux
Alternative to print on a single line
I have a script that prints the x, y coordinates of the mouse as such:
import pyautogui
import time
while True:
x, y = pyautogui.position()
position_string = "X: {} Y: {}".format(str(x).rjust(4), str(y).rjust(4))
print(position_string, end='')
print('\b' * len(position_string), end='', flush=True)
time.sleep(1)
Where I will point out that you can print the backspace character ('\b') the amount of times that there are characters on the screen (len(position_string)), and when used with the end='' and flush=True options this will constantly print on a single line within your console. I should also note that this does not work in IDLE, but only on an actual command line! In IDLE the backspace characters are actually printed as some weird square shape...
This is called ANSI escape code . 2K is the name for Erase in Line. Quote from the link:
Erases part of the line. If n is 0 (or missing), clear from cursor to the end of the line. If n is 1, clear from cursor to beginning of the line. If n is 2, clear entire line. Cursor position does not change.
You can also try echo -e '\x1b[2k' in the terminal for better understanding.

Python 2.7 VSCODE doesn't get the correct length of input string

in my class we are studying python 2.7. I am using vscode to test the exercises.
exercise 1: read user input and print the length. If the user write
exit the program finish.
My code is follow:
myexit=False
while (myexit!=True):
#read user input
txt=raw_input("write a string or write exit to go out: ")
#print the user input string
print txt
if (str(txt)=='exit'):
myexit=True#exit from while
else:
print len(txt) #print the string length
print "finish"
when i test the code i get always the length of the string +1
example: if i write foo the output is 4 and no 3. When i write exit i
don't go out from the while and the output is 5.
Where i wrong ?
I have missed a module?
Thanks for your help
I am not sure exactly why this is happening, and I don't have access to a windows machine to test/verify but based on the comments above, it appears that on the version of python you are using that raw_input is only stripping the newline(\n) and not the carriage return(\r). Windows uses \r\n while unix uses \n. When raw input returns the \r is still on the string, hence the extra char. A useful debugging technique at the cli is to use the function repr() on the value to see exactly how it is represented. This is helpful to locate any stray control or invisible chars in strings.
The function rstrip() will remove all whitespace from the right side of the string, which in this case should safely remove the stray \r. It should also be safe if this code is running on a *nix like system as rstrip() will only remove the whitespace if it is present. You can also specify a set of char to strip, so if you would would like to be pedantic, you could use rstrip("\r").
txt=raw_input("write a string or write exit to go out: ").rstrip("\r")
Should fix the issue while still maintaining compatibility on different versions.

Python variables stored in text files not working, but should be

I've settled on a text-file based save system for my game, storing the values of required variables with keywords - for example, the password that tells the game which chapter to play. However, it appears to be malfunctioning, and I can't see why.
Before starting the game, we have:
if not os.file.isfile('TSGsave{0}.txt'.format(name)):
TSGsave=open('TSGsave{0}.txt'.format(name),'wt')
TSGsave.write('\nw5CT$n<jfW=-#J%4Ya5##')
TSGsave.close()
(the keyword used is a bunch of jibberish so that the user can't change it knowing what's going to happen). This adds w5CT$n<jfW=-#J%4Ya5## to the text file. We then have:
for i in range (len(lines)):
if 'w5CT$n<jfW' in lines[i]:
findpass=lines[i]
for i in range (len(findpass)):
if findpass[i]=='=':
cutfrom=i+1
password=findpass[cutfrom:len(findpass)]
to retrieve the variable (which can change, so it can't be written in as definite value). I know it works, because I added print (password) to the code and it returned -#J%4Ya5##. Then to start the corresponding chapter, the code is:
if password=='-#J%4Ya5##':
but it isn't starting the indented block. In the shell, the program ends and goes back to the >>> line.
If there is a way to fix this code, great - but another code to do the same thing would work just as well.
Your lines contain newlines, and these are being included. Strip these from the line:
findpass = lines[i].rstrip('\n')
Printing a value with a newline in it will simply add an extra black line after the print. Always use the repr() function to produce a Python representation of strings to see such characters:
>>> print '-#J%4Ya5##\n'
-#J%4Ya5##
>>> print repr('-#J%4Ya5##\n')
'-#J%4Ya5##\n'
Your parsing code is overly complicated; you can use str.split() or str.partition() to split your password from the line instead. You should just loop over the lines list directly rather than produce indices with range():
for line in lines:
if 'w5CT$n<jfW' in line:
password = line.partition('=')[2].rstrip('\n')

Deleting already printed in Python

For practice, I'm trying to do some stuff in Python. I've decided to make a simple hangman game - I'm not making a GUI. The game would start with a simple input(). Now, I'd like next line to, beside asking for input, to delete the hidden word. I've tried using \b (backspace character), but it's not working. Something like:
word = input("Your word: ")
for i in range(len(word) + 12):
print("\b")
Now, printing the backlash character is supposed to delete the input and "Your word", but it isn't doing anything. If I do this in IDLE I get squares, and I get nothing if I open it by clicking.
How to accomplish this? I'm afraid I wasn't too clear with my question, but I hope you'll see what I meant. :)
\b does not erase the character before the cursor, it simply moves the cursor left one column. If you want text entry without echoing the characters then look at getpass.
I assume the player entering the word wants to be sure they've entered it correctly so you probably want to display the word as they're typing it right?
How about printing enough \ns to move it off the screen when they're done or issue a clear screen command?
You mentioned this was a simple game so a simple solution seems fitting.
[Edit] Here's a simple routine to clear the console on just about any platform (taken from here):
def clearscreen(numlines=100):
"""Clear the console.
numlines is an optional argument used only as a fall-back.
"""
import os
if os.name == "posix":
# Unix/Linux/MacOS/BSD/etc
os.system('clear')
elif os.name in ("nt", "dos", "ce"):
# DOS/Windows
os.system('CLS')
else:
# Fallback for other operating systems.
print '\n' * numlines
word = raw_input("Your word: ")
import sys
sys.stdout.write("\x1b[1A" + 25*" " + "\n")
This will replace the last line printed with 25 spaces.
I think part of your problem is that input is echoing the Enter that terminates your word entry. Your backspaces are on another line, and I don't think they'll back up to the previous line. I seem to recall a SO question about how to prevent that, but I can't find it just now.
Also, I believe print, by default, will output a newline on each call, so each backspace would be on its own line. You can change this by using an end='' argument.
Edit: I found the question I was thinking of, but it doesn't look like there's any help there. You can look at it if you like: Python input that ends without showing a newline

Categories