Я хотел бы сделать несколько операторов, которые выдавали бы стандартный вывод, не видя новых строк между операторами.
В частности, предположим, что у меня есть:
for item in range(1,100):
print item
В результате получаем:
1
2
3
4
.
.
.
Как сделать так, чтобы вместо этого получилось:
1 2 3 4 5 ...
Еще лучше, можно ли вывести единственное число над последним числом, чтобы на экране одновременно было только одно число?
Измените print item
на:
print item,
в Python 2.7print(item, end=" ")
в Python 3Если необходимо вывести данные динамически, используйте следующий синтаксис:
print(item, sep=' ', end='', flush=True)
в Python 3Кстати...... Как обновлять его каждый раз, чтобы он печатал ми в одном месте, просто меняйте номер.
В общем, способ сделать это с кодами управления терминалами. Это особенно простой случай, для которого вам нужен только один специальный символ: U + 000D CARRIAGE RETURN, который написан `' \ r '' на Python (и многих других языках). Вот полный пример, основанный на вашем коде:
from sys import stdout
from time import sleep
for i in range(1,20):
stdout.write("\r%d" % i)
stdout.flush()
sleep(1)
stdout.write("\n") # move the cursor to the next line
Некоторые вещи об этом могут быть удивительными
\ r
идет в начале строки так, что во время работы программы курсор всегда будет после числа. Это не просто косметика: некоторые терминальные эмуляторы очень запутаются, если вы делаете это наоборот.Если вы обнаружите, что это не работает, первое, что вы должны заподозрить, это то, что ваш эмулятор терминала глючит. Программа vttest может помочь вам протестировать ее.
Вы можете заменить stdout.write
на оператор print
, но я предпочитаю не смешивать print
с прямым использованием объектов файла.
Используйте print item,
, чтобы в операторе печати не было новой строки.
В Python 3 это print(item, end=" ")
.
Если вы хотите, чтобы каждое число отображалось в одном и том же месте, используйте, например, (Python 2.7):
to = 20
digits = len(str(to - 1))
delete = "\b" * (digits + 1)
for i in range(to):
print "{0}{1:{2}}".format(delete, i, digits),
В Python 3 все несколько сложнее, здесь необходимо промыть sys.stdout
, иначе после завершения цикла ничего не будет выведено:
import sys
to = 20
digits = len(str(to - 1))
delete = "\b" * (digits)
for i in range(to):
print("{0}{1:{2}}".format(delete, i, digits), end="")
sys.stdout.flush()
Как и другие примеры Я использую аналогичный подход, но вместо того, чтобы тратить время на вычисление последней длины вывода и т. Д
Я просто использую экранирование кода ANSI, чтобы вернуться к началу строки, а затем очистить всю строку перед печатью вывода текущего состояния.
import sys
class Printer():
"""Print things to stdout on one line dynamically"""
def __init__(self,data):
sys.stdout.write("\r\x1b[K"+data.__str__())
sys.stdout.flush()
Чтобы использовать в своей итерационной петле, вы просто называете что-то вроде:
x = 1
for f in fileList:
ProcessFile(f)
output = "File number %d completed." % x
Printer(output)
x += 1
Вы можете добавить конечную запятую в свой оператор печати, чтобы распечатать пробел вместо новой строки в каждой итерации:
print item,
В качестве альтернативы, если вы используете Python 2.6 или более позднюю версию, вы можете использовать новую функцию печати, которая позволит вам указать, что даже в конце каждого печатаемого элемента не должно быть места (или вы можете указать любой конец, который вы хотите):
from __future__ import print_function
...
print(item, end="")
Наконец, вы можете записать непосредственно в стандартный вывод, импортировав его из модуля sys, который возвращает файлоподобный объект:
from sys import stdout
...
stdout.write( str(item) )
изменение
print item
к
print "\033[K", item, "\r",
sys.stdout.flush()
Еще один ответ, который я использую на 2.7, где я просто распечатываю ".«каждый раз, когда цикл запускается (чтобы указать пользователю, что все еще работает), это:
print "\b.",
Это печатает ".«символы без пробелов между каждым. Это выглядит немного лучше и работает довольно хорошо. \ B - это символ свободного пространства для тех, кто интересуется.
"Кстати...... Как обновлять его каждый раз, чтобы он печатал ми в одном месте, просто меняйте номер.«
Это действительно сложная тема. То, что предложил zack (вывод кодов управления консолью), является одним из способов достижения этого.
Вы можете использовать (n) корсы, но это работает в основном на * nixes.
В Windows (и здесь идет интересная часть), которая редко упоминается (я не могу понять почему), вы можете использовать привязки Python к WinAPI ([http://sourceforge.net/projects/pywin32/](http://sourceforge .net / projects / pywin32 /) также с ActivePython по умолчанию) - это не так сложно и хорошо работает. Вот небольшой пример:
import win32console, time
output_handle = win32console.GetStdHandle( win32console.STD_OUTPUT_HANDLE )
info = output_handle.GetConsoleScreenBufferInfo()
pos = info["CursorPosition"]
for i in "\\|/-\\|/-":
output_handle.WriteConsoleOutputCharacter( i, pos )
time.sleep( 1 )
Или, если вы хотите использовать print
(заявление или функция, без разницы):
import win32console, time
output_handle = win32console.GetStdHandle( win32console.STD_OUTPUT_HANDLE )
info = output_handle.GetConsoleScreenBufferInfo()
pos = info["CursorPosition"]
for i in "\\|/-\\|/-":
print i
output_handle.SetConsoleCursorPosition( pos )
time.sleep( 1 )
Модуль win32console
позволяет вам делать гораздо более интересные вещи с консолью Windows... Я не большой поклонник WinAPI, но недавно я понял, что по крайней мере половина моей антипатии к нему была вызвана написанием кода WinAPI на C - питонические привязки намного проще в использовании.
Все остальные ответы, конечно, отличные и питонические, но... Что если я захочу напечатать на предыдущей строке? Или напишите многострочный текст, затем очистите его и снова напишите те же строки? Мое решение делает это возможным.
Чтобы числа перезаписывали друг друга, вы можете сделать что-то вроде этого:
for i in range(1,100):
print "\r",i,
Это должно работать до тех пор, пока номер напечатан в первом столбце.
РЕДАКТИРОВАТЬ: Вот версия, которая будет работать, даже если она не напечатана в первом столбце.
prev_digits = -1
for i in range(0,1000):
print("%s%d" % ("\b"*(prev_digits + 1), i)),
prev_digits = len(str(i))
Следует отметить, что этот код был протестирован и отлично работает на Python 2.5 в Windows, на консоли WIndows. По мнению некоторых других, для просмотра результатов может потребоваться промывка крепкого тела. YMMV .
Так много сложных ответов. Если у вас есть python 3, просто поместите \ r
в начале печати и добавьте к нему end = '', flush = True
:
время импорта
для i в диапазоне (10):
print (f '\ r {i} foo bar', end = '', flush = True)
time.sleep (0,5)
Это будет писать 0 foo bar
, затем 1 foo bar
и т. Д. На месте.
для Python 2.7
for x in range(0, 3):
print x,
для Python 3
for x in range(0, 3):
print(x, end=" ")
In [9]: print?
Type: builtin_function_or_method
Base Class: <type 'builtin_function_or_method'>
String Form: <built-in function print>
Namespace: Python builtin
Docstring:
print(value, ..., sep=' ', end='\n', file=sys.stdout)
Prints the values to a stream, or to sys.stdout by default.
Optional keyword arguments:
file: a file-like object (stream); defaults to the current sys.stdout.
sep: string inserted between values, default a space.
end: string appended after the last value, default a newline.
Если вы просто хотите распечатать цифры, вы можете избежать цикла.
# python 3
import time
startnumber = 1
endnumber = 100
# solution A without a for loop
start_time = time.clock()
m = map(str, range(startnumber, endnumber + 1))
print(' '.join(m))
end_time = time.clock()
timetaken = (end_time - start_time) * 1000
print('took {0}ms\n'.format(timetaken))
# solution B: with a for loop
start_time = time.clock()
for i in range(startnumber, endnumber + 1):
print(i, end=' ')
end_time = time.clock()
timetaken = (end_time - start_time) * 1000
print('\ntook {0}ms\n'.format(timetaken))
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 51 52 53 54 55 56 57 58 59 60 61 62 63 64 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83взял 21.1986929975мс
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 51 52 53 54 55 56 57 58 59 60 61 62 63 64 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 взял 491,466823551мс
Запятая в конце заявления печати пропускает новую строку.
for i in xrange(1,100):
print i,
но это не перезаписывает.
В Python 3 вы можете сделать это так:
for item in range(1,10):
print(item, end =" ")
Выходы:
1 2 3 4 5 6 7 8 9
кортеж: Вы можете сделать то же самое с кортежем:
tup = (1,2,3,4,5)
for n in tup:
print(n, end = " - ")
Выходы:
1 - 2 - 3 - 4 - 5 -
Другой пример:
list_of_tuples = [(1,2),('A','B'), (3,4), ('Cat', 'Dog')]
for item in list_of_tuples:
print(item)
Выходы:
(1, 2)
('A', 'B')
(3, 4)
('Cat', 'Dog')
Вы даже можете распаковать свой кортеж следующим образом:
list_of_tuples = [(1,2),('A','B'), (3,4), ('Cat', 'Dog')]
# Tuple unpacking so that you can deal with elements inside of the tuple individually
for (item1, item2) in list_of_tuples:
print(item1, item2)
Выходы:
1 2
A B
3 4
Cat Dog
еще один вариант:
list_of_tuples = [(1,2),('A','B'), (3,4), ('Cat', 'Dog')]
for (item1, item2) in list_of_tuples:
print(item1)
print(item2)
print('\n')
Выходы:
1
2
A
B
3
4
Cat
Dog