Печать в одну строку, а не новую строку в python

В принципе, я хочу сделать противоположное тому, что сделал этот парень... хе-хе.

Python Script: каждый раз печатать новую строку для оболочки, а не для обновления существующей строки

У меня есть программа, которая говорит мне, как далеко продвинулся.

for i in some_list:
    #do a bunch of stuff.
    print i/len(some_list)*100," percent complete"

Итак, если len (some_list) было 50, я бы получил последнюю строку, напечатанную 50 раз. Я хочу напечатать одну строку и продолжить обновление этой строки. Я знаю, что знаю, что это, вероятно, самый лёгкий вопрос, который вы будете читать весь день. Я просто не могу понять, какие четыре слова мне нужно отправить в Google, чтобы получить ответ.

Update! Я попробовал предложение mvds, которое SEEMED было правильным. Новый код

print percent_complete,"           \r",

Процент завершен - это просто строка (я впервые абстрагировался, пытаясь быть буквальным). Теперь результат заключается в том, что он запускает программу, не печатает "НИЧЕГО" до завершения программы, а затем печатает "100% завершен" на одной и только одной строке.

Без возврата каретки (но с запятой, половиной предложения mvds) он ничего не печатает до конца. И затем печатает:

0 percent complete     2 percent complete     3 percent complete     4 percent complete    

И так далее. Итак, теперь новая проблема заключается в том, что с запятой она не печатается до завершения программы.

С возвратом каретки и без запятой он ведет себя точно так же, как и ни с одним из них.

Ответ 1

Он назвал возврат каретки, или \r

Использование

print i/len(some_list)*100," percent complete         \r",

Запятая предотвращает печать с добавлением новой строки. (и пробелы будут держать линию очищенной от предыдущего выхода)

Кроме того, не забудьте завершить с print "", чтобы получить хотя бы завершающую строку новой строки!

Ответ 2

Из python 3.x вы можете:

print('bla bla', end='')

(который также может использоваться в Python 2.6 или 2.7, помещая from __future__ import print_function в начало вашего script/модуля)

Пример панели прогресса консоли Python:

import time

# status generator
def range_with_status(total):
    """ iterate from 0 to total and show progress in console """
    n=0
    while n<total:
        done = '#'*(n+1)
        todo = '-'*(total-n-1)
        s = '<{0}>'.format(done+todo)
        if not todo:
            s+='\n'        
        if n>0:
            s = '\r'+s
        print(s, end='')
        yield n
        n+=1

# example for use of status generator
for i in range_with_status(10):
    time.sleep(0.1)

Ответ 3

Для меня то, что работало, было комбо ответов Реми и Сириуса:

from __future__ import print_function
import sys

print(str, end='\r')
sys.stdout.flush()

Ответ 4

для консоли вам, вероятно, понадобится

sys.stdout.flush()

для принудительного обновления. Я думаю, что использование , в печати блокирует stdout от промывки и как-то не обновит

Ответ 5

Никто не упомянул, что в Python 3. 3+ вам не нужен sys.stdout.flush(). print('foobar', end='', flush=True) работает.

Ответ 6

Это работает для меня, взломав его один раз, чтобы увидеть, возможно ли это, но никогда не используется в моей программе (графический интерфейс гораздо приятнее):

import time
f = '%4i %%'
len_to_clear = len(f)+1
clear = '\x08'* len_to_clear
print 'Progress in percent:'+' '*(len_to_clear),
for i in range(123):
    print clear+f % (i*100//123),
    time.sleep(0.4)
raw_input('\nDone')

Ответ 7

import time
import sys


def update_pct(w_str):
    w_str = str(w_str)
    sys.stdout.write("\b" * len(w_str))
    sys.stdout.write(" " * len(w_str))
    sys.stdout.write("\b" * len(w_str))
    sys.stdout.write(w_str)
    sys.stdout.flush()

for pct in range(0, 101):
    update_pct("{n}%".format(n=str(pct)))
    time.sleep(0.1)

\b переместит местоположение курсора назад на одно пространство
Таким образом, мы перемещаем его полностью до начала строки
Затем мы записываем пробелы, чтобы очистить текущую строку. Когда мы записываем пробелы, курсор перемещается вперед/вправо одним Итак, мы должны переместить курсор назад в начале строки, прежде чем писать наши новые данные

Протестировано на Windows cmd с использованием Python 2.7

Ответ 8

Попробуйте следующее:

for i in some_list:
    #do a bunch of stuff.
    print i/len(some_list)*100," percent complete",

(с запятой в конце.)

Ответ 9

На основе ответа Реми для Python 2.7+ используйте это:

from __future__ import print_function
import time

# status generator
def range_with_status(total):
    """ iterate from 0 to total and show progress in console """
    import sys
    n = 0
    while n < total:
        done = '#' * (n + 1)
        todo = '-' * (total - n - 1)
        s = '<{0}>'.format(done + todo)
        if not todo:
            s += '\n'
        if n > 0:
            s = '\r' + s
        print(s, end='\r')
        sys.stdout.flush()
        yield n
        n += 1


# example for use of status generator
for i in range_with_status(50):
    time.sleep(0.2)

Ответ 10

Для Python 3.6+ и для любого list а не только для int, а также используя всю ширину окна консоли и не переходя на новую строку, вы можете использовать следующее:

примечание: обратите внимание, что функция get_console_with() будет работать только в системах на базе Linux, и поэтому вам придется переписать ее для работы в Windows.

import os
import time

def get_console_width():
    """Returns the width of console.

    NOTE: The below implementation works only on Linux-based operating systems.
    If you wish to use it on another OS, please make sure to modify it appropriately.
    """
    return int(os.popen('stty size', 'r').read().split()[1])


def range_with_progress(list_of_elements):
    """Iterate through list with a progress bar shown in console."""

    # Get the total number of elements of the given list.
    total = len(list_of_elements)
    # Get the width of currently used console. Subtract 2 from the value for the
    # edge characters "[" and "]"
    max_width = get_console_width() - 2
    # Start iterating over the list.
    for index, element in enumerate(list_of_elements):
        # Compute how many characters should be printed as "done". It is simply
        # a percentage of work done multiplied by the width of the console. That
        # is: if we're on element 50 out of 100, that means we're 50% done, or
        # 0.5, and we should mark half of the entire console as "done".
        done = int(index / total * max_width)
        # Whatever is left, should be printed as "unfinished"
        remaining = max_width - done
        # Print to the console.
        print(f'[{done * "#"}{remaining * "."}]', end='\r')
        # yield the element to work with it
        yield element
    # Finally, print the full line. If you wish, you can also print whitespace
    # so that the progress bar disappears once you are done. In that case do not
    # forget to add the "end" parameter to print function.
    print(f'[{max_width * "#"}]')


if __name__ == '__main__':
    list_of_elements = ['a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j']
    for e in range_with_progress(list_of_elements):
        time.sleep(0.2)

Ответ 11

Поздно к игре - но так как ни один из ответов не работал для меня (я не пробовал их все), и я встречал этот ответ более одного раза в своих поисках... В Python 3 это решение довольно элегантно и я считаю, что делает именно то, что ищет автор, он обновляет одно утверждение в той же строке. Обратите внимание, что вам может потребоваться сделать что-то особенное, если линия сжимается, а не увеличивается (например, возможно, сделайте строку фиксированной длины с отступами в конце)

if __name__ == '__main__':
    for i in range(100):
        print("", end=f"\rPercentComplete: {i} %")
        time.sleep(0.2)