进度显示¶
RICH可以显示有关长时间运行的任务/文件副本等的持续更新的进度信息。显示的信息是可配置的,默认情况下将显示‘任务’的描述、进度条、完成百分比和估计剩余时间。
丰富的进度显示支持多个任务,每个任务都有一个栏和进度信息。您可以使用它来跟踪工作在线程或进程中发生的并发任务。
要查看进度显示的外观,请从命令行尝试执行以下操作::
python -m rich.progress
备注
Progress适用于Jupyter笔记本电脑,但需要注意的是,自动刷新功能被禁用。您需要显式调用 refresh()
或设置 refresh=True
当呼叫时 update()
。或使用 track()
在每个循环上自动执行刷新的功能。
基本用法¶
有关基本用法,请调用 track()
函数,该函数接受序列(如列表或范围对象)和您正在处理的作业的可选描述。Track函数将从序列中产生值,并更新每次迭代的进度信息。以下是一个示例:
import time
from rich.progress import track
for i in track(range(20), description="Processing..."):
time.sleep(1) # Simulate work being done
高级用法¶
如果需要在显示中显示多个任务,或者希望配置进度显示中的列,可以直接使用 Progress
班级。构建了Progress对象后,使用以下命令添加任务(S (add_task()
),并更新进度 update()
。
Progress类被设计为用作 context manager 这将自动启动和停止进度显示。
下面是一个简单的例子::
import time
from rich.progress import Progress
with Progress() as progress:
task1 = progress.add_task("[red]Downloading...", total=1000)
task2 = progress.add_task("[green]Processing...", total=1000)
task3 = progress.add_task("[cyan]Cooking...", total=1000)
while not progress.finished:
progress.update(task1, advance=0.5)
progress.update(task2, advance=0.3)
progress.update(task3, advance=0.9)
time.sleep(0.02)
这个 total
与任务关联的值是进度达到100%所必须完成的步骤数。一个 step 在这个上下文中,任何对您的应用程序有意义的东西都可以;它可以是文件读取的字节数,或者处理的图像数,等等。
正在更新任务¶
当你打电话的时候 add_task()
你会得到一个 Task ID 。使用此ID呼叫 update()
只要你完成了某项工作,或者任何信息发生了变化。通常,您将需要更新 completed
每次你完成了一个步骤。您可以通过设置 completed
直接或通过设置 advance
这将增加目前的 completed
价值。
这个 update()
方法收集也与任务关联的关键字参数。使用此选项可以提供要在进度显示中呈现的任何其他信息。其他参数存储在 task.fields
,并可在 Column classes 。
隐藏任务¶
您可以通过更新任务来显示或隐藏任务 visible
价值。默认情况下,任务是可见的,但也可以通过调用 add_task()
使用 visible=False
。
暂时性进展¶
通常,当您退出进度上下文管理器(或调用 stop()
)最后刷新的显示保留在终端中,光标在下面一行上。您还可以通过设置使进度显示在退出时消失 transient=True
在Progress构造函数上。以下是一个示例:
with Progress(transient=True) as progress:
task = progress.add_task("Working", total=100)
do_work(task)
如果您希望在任务完成时终端中的输出更少,则瞬时进度显示非常有用。
不确定的进展¶
添加任务时,它会自动 started 这意味着它将显示0%的进度条,剩余时间将从当前时间计算。如果在开始更新进度之前有很长的延迟,这可能不起作用;例如,您可能需要等待服务器的响应或对目录中的文件进行计数。在这些情况下,您可以调用 add_task()
使用 start=False
或 total=None
它将显示一个脉冲动画,让用户知道有什么东西在工作。这就是众所周知的 indeterminate 进度条。当您有了可以调用的步骤数时 start_task()
它将以0%的速度显示进度条,然后 update()
像往常一样。
自动刷新¶
默认情况下,进度信息每秒刷新10次。可以使用设置刷新率 refresh_per_second
关于 Progress
构造函数。如果您知道您的更新不会那么频繁,则应将其设置为低于10的值。
如果您的更新不是很频繁,您可能希望完全禁用自动刷新,这可以通过设置 auto_refresh=False
在构造函数上。如果禁用自动刷新,则需要调用 refresh()
更新您的任务后手动(S)。
展开¶
进度条(S)将只使用显示任务信息所需的终端宽度。如果您将 expand
参数,则Rich会将进度显示拉伸到最大可用宽度。
立柱¶
您可以使用位置参数自定义进度显示中的列 Progress
构造函数。这些列被指定为 format string 或者是 ProgressColumn
对象。
格式字符串将使用单个值呈现 "task" 这将是一个 Task
举个例子。例如 "{task.description}"
将在列中显示任务描述,并且 "{task.completed} of {task.total}"
将显示总共已完成多少个步骤。通过关键字参数传递给 ~rich.progress.Progress.update 存储在 task.fields
。您可以使用以下语法将它们添加到格式字符串中: "extra info: {task.fields[extra]}"
。
默认列相当于以下列:
progress = Progress(
TextColumn("[progress.description]{task.description}"),
BarColumn(),
TaskProgressColumn(),
TimeRemainingColumn(),
)
要在默认列之外使用您自己的列创建进度,请使用 get_default_columns()
**
progress = Progress(
SpinnerColumn(),
*Progress.get_default_columns(),
TimeElapsedColumn(),
)
以下列对象可用:
BarColumn
显示条形图。TextColumn
显示文本。TimeElapsedColumn
显示经过的时间。TimeRemainingColumn
显示估计的剩余时间。MofNCompleteColumn
将完成进度显示为"{task.completed}/{task.total}"
(如果已完成且总数为整型,则效果最好)。FileSizeColumn
以文件大小显示进度(假设步长为字节)。TotalFileSizeColumn
显示文件总大小(假设步长为字节)。DownloadColumn
显示下载进度(假设步骤为字节)。TransferSpeedColumn
显示传输速度(假设步长为字节)。SpinnerColumn
显示“微调”动画。RenderableColumn
在列中显示任意丰富可渲染对象。
若要实现您自己的列,请扩展 ProgressColumn
类,并像使用其他列一样使用它。
表列¶
里奇建立了一个 Table
用于Progress实例中的任务。您可以自定义此列的 tasks table 通过指定 table_column
参数,该参数应该是一个 Column
举个例子。
以下示例演示了一个进度条,其中说明占终端宽度的三分之一,该条占其余三分之二:
from time import sleep
from rich.table import Column
from rich.progress import Progress, BarColumn, TextColumn
text_column = TextColumn("{task.description}", table_column=Column(ratio=1))
bar_column = BarColumn(bar_width=None, table_column=Column(ratio=2))
progress = Progress(text_column, bar_column, expand=True)
with progress:
for n in progress.track(range(100)):
progress.print(n)
sleep(0.1)
打印/记录¶
Progress类将创建一个内部控制台对象,您可以通过 progress.console
。如果您打印或登录到此控制台,则会显示输出 above 进度显示。以下是一个示例:
with Progress() as progress:
task = progress.add_task("twiddling thumbs", total=10)
for job in range(10):
progress.console.print(f"Working on job #{job}")
run_job(job)
progress.advance(task)
如果您有另一个要使用的控制台对象,请将其传递给 Progress
构造函数。以下是一个示例:
from my_project import my_console
with Progress(console=my_console) as progress:
my_console.print("[bold blue]Starting work!")
do_work(progress)
重定向标准输出/标准错误¶
为了避免破坏进度显示的视觉效果,Rich将重定向 stdout
和 stderr
这样您就可以使用内置的 print
陈述。默认情况下,此功能处于启用状态,但您可以通过设置 redirect_stdout
或 redirect_stderr
至 False
自定义¶
如果 Progress
类并不能提供您在进度显示方面所需的内容,您可以重写 get_renderables
方法。例如,下面的类将呈现一个 Panel
在进度显示周围:
from rich.panel import Panel
from rich.progress import Progress
class MyProgress(Progress):
def get_renderables(self):
yield Panel(self.make_tasks_table(self.tasks))
正在从文件中读取¶
Rich提供了一种在读取文件时生成进度条的简单方法。如果你打电话给 open()
它将返回一个上下文管理器,在您阅读时显示一个进度条。当您不能轻松修改执行读取的代码时,这尤其有用。
下面的示例演示了如何在读取JSON文件时显示进度:
import json
import rich.progress
with rich.progress.open("data.json", "rb") as file:
data = json.load(file)
print(data)
如果您已经有一个文件对象,则可以调用 wrap_file()
它返回一个上下文管理器,该管理器包装您的文件,以便它显示一个进度条。如果您使用此函数,则需要设置预期读取的字节数或字符数。
下面是一个从Internet读取URL的示例::
from time import sleep
from urllib.request import urlopen
from rich.progress import wrap_file
response = urlopen("https://www.textualize.io")
size = int(response.headers["Content-Length"])
with wrap_file(response, size) as file:
for line in file:
print(line.decode("utf-8"), end="")
sleep(0.1)
如果希望从多个文件中读取数据,可以使用 open()
或 wrap_file()
若要将文件进度添加到现有的Progress实例,请执行以下操作。
看见 cp_progress.py 对于最小的克隆 cp
命令,该命令在复制文件时显示进度条。
多重进步¶
对于单个Progress实例,每个任务不能有不同的列。但是,您可以在 现场展示 。看见 live_progress.py 和 dynamic_progress.py 有关使用多个Progress实例的示例。
示例¶
看见 downloader.py 用于进度显示的真实应用。此脚本可以下载多个并发文件,并带有进度条、传输速度和文件大小。