loguru 日志库快速入门

news/2025/9/27 21:52:39/文章来源:https://www.cnblogs.com/surpassme/p/19115757

1.loguru

1.1 loguru 介绍

    loguru是一个功能强大且非常容易使用的第三方开源Python日志管理库。它建立在Python标准库中的logging模块之上,并提供了更加简洁直观、功能丰富的接口。github仓库地址:https://github.com/Delgan/loguru

1.2 安装

    想要快速体验其功能,首先需要安装该库,安装命令如下所示:

$ pip install loguru

1.3 基本用法

    在安装完成,我们就可以来快速体验其功能了,如下所示:

1.3.1 快速使用

from loguru import loggerlogger.info("这是一条INFO信息")
logger.debug("这是一条DEBUG信息")
logger.warning("这是一条WARNING信息")
logger.error("这是一条ERROR信息")
logger.critical("这是一条CRITICAL信息")

    输出结果如下所示:

01-快速使用演示.png

    loguru 日志输出默认格式如下:

  • 时间戳:日志记录的具体时间,格式通常为年-月-日 时:分:秒.毫秒
  • 日志级别:当前这条日志的严重性级别
  • 模块名称:表示日志来自哪个模块
  • 函数或作用域范围:表示日志来自哪个函数或作用域范围
  • 行号:触发日志所在的行号
  • 日志消息:实际的日志内容

    每条日志被特定的分隔符分隔并显示,默认分隔符为 |。同时loguru 也支持 使用颜色 来区分不同的日志级别,使得日志输出更加直观。如果默认功能不能满足需求,也可以进行自定义。

    loguru 默认会将日志输出到 standard error stream (stderr),loguru这样做是为了把日志输出与你的应用程序日志分开。如果需要更复杂的日志配置,你也可以自定义配置,例如将日志存储到文件、发送到网络服务中等。

1.3.2 日志级别

1.3.2.1 日志级别介绍

    通过前面的快速使用,相信你已经对loguru有了一个基本的了解。为了更好的根据日志级别进行分类,loguru 根据其日志的重要性,定义了日志级别分类。如下所示:

级别 方法 数值 目的
TRACE logger.trace() 5 最详细的日志记录,常用于追踪代码执行过程
DEBUG logger.debug() 10 用于记录详细的程序调试信息,一般用于开发阶段
INFO logger.info() 20 用于记录常规消息记录
SUCCESS logger.success() 25 用于记录一些操作成功的消息记录
WARNING logger.warning() 30 用于记录一些可能不是错误,但需要关注的消息记录
ERROR logger.error() 40 用于记录错误信息,这些错误可能会影响程序某些功能,但不会导致出现崩溃或停止运行
CRITICAL logger.critical() 50 用于记录非常严重的错误信息,这些错误通常会导致程序出现崩溃或停止运行

1.3.2.2 调整日志级别

    默认情况下,loguru的日志级别为DEBUG(10) 因此loguru会记录并显示日志级别为DEBUG及以上级别的消息记录。这也就意味着,在你第一次使用loguru打印日志时,会显示除TRACE级别以外的所有日志信息。

    如果想要开启TRACE级别的日志记录,可以自行调整最小日志级别,可以使用logger.add()方法,如下所示:

import sys
from loguru import logger# 修改日志最小级别
logger.add(sys.stderr,level="TRACE")logger.info("这是一条INFO信息")
logger.debug("这是一条DEBUG信息")
logger.warning("这是一条WARNING信息")
logger.error("这是一条ERROR信息")
logger.critical("这是一条CRITICAL信息")
logger.trace("这是一条TRACE信息")

    输出结果如下所示:

02-调整日志级别.png

    通过上述代码,我们导入了sys模块并且将输出重定向于sys.stderr。通过logger.add()方法添加了一个新的handler,这样我们就成功修改了loguru默认的日志级别,并将日志输出到sys.stderr中。

    通过调用loggeer.add()方法之后,会返回一个唯一值(handler_id),用于标识handler。后面我们可以调用方法logger.remove(handler_id)来移除handler。示例如下所示:

import sys
from loguru import loggerdef print_log():logger.info("~~"*30)logger.info("这是一条INFO信息")logger.debug("这是一条DEBUG信息")logger.warning("这是一条WARNING信息")logger.error("这是一条ERROR信息")logger.critical("这是一条CRITICAL信息")logger.trace("这是一条TRACE信息")if __name__ == '__main__':# 修改日志最小级别handler_id=logger.add(sys.stderr,level="TRACE")logger.info(f"handler id:{handler_id}")print_log()logger.remove(handler_id)print_log()

    输出结果如下所示:

03-删除自定义日志handler.png

    调用logger.remove()方法时,如果不传入参数值,则默认删除所有已经存在的handler,并且包含默认的handler。通过这个方法,我们就可以实现在创建新的handler之前,删除所有已经存在的handler。

loguru中默认的handler_id为0,如果需要删除默认的handler,在调用logger.remove()中传入0即可。如果需要删除其他新增的handler,为避免出现不是期望的结果,建议传入明确的handler_id值。

    在理解了loguru的日志级别之后,我们就可以根据需要选择合适的日志级别策略。例如在开发环境中,可以使用DEBUG级别,在生产环境中,可以使用WARNING或以上的日志级别。

1.3.3 自定义日志

1.3.3.1 日志参数

    在loguru中,add函数用于添加日志处理器。这个函数用于指定日志消息应该被发送到何处,例如控制台、文件或其他自定义的目的地。其定义如下所示:

def add(self,sink: Union[TextIO, Writable, Callable[[Message], None], Handler],*,level: Union[str, int] = ...,format: Union[str, FormatFunction] = ...,filter: Optional[Union[str, FilterFunction, FilterDict]] = ...,colorize: Optional[bool] = ...,serialize: bool = ...,backtrace: bool = ...,diagnose: bool = ...,enqueue: bool = ...,context: Optional[Union[str, BaseContext]] = ...,catch: bool = ...
) -> int: ...

    add函数主要参数介绍如下:

  • sink: 定义日志消息的输出位置,可以是文件路径、标准输出(stdout)、标准错误(stderr,默认)或其他自定义的输出位置。
  • format: 指定日志消息的格式,可以是简单的字符串,也可以是格式化字符串,支持各种字段插值。
  • level: 设置处理程序处理的日志消息的最低级别。比如设置为DEBUG,则处理程序将处理DEBUG以上所有级别的日志消息。
  • filter: 可选参数,用于添加过滤器,根据特定的条件过滤掉不需要的日志消息。
  • colorize: 布尔值,指定是否对日志消息进行着色处理,使日志在控制台中更易于区分。
  • serialize: 布尔值,指定是否对日志消息进行序列化处理,通常与enqueue=True一起使用,以确保多线程安全。
  • enqueue: 布尔值,指定是否将日志消息放入队列中处理,用于多线程应用中避免阻塞。
  • backtrace: 布尔值或字符串,指定是否记录回溯信息,默认为False。
  • diagnose: 布尔值,启用后,会在处理程序内部出现错误时记录诊断信息。
  • rotation: 日志文件轮换的配置,支持按大小或时间进行日志文件的轮换。
  • retention: 用于设置日志文件的保留时间。
  • compression: 布尔值,指定是否对轮换后的日志文件进行压缩处理。

1.3.3.2 开发实践

    loguru 默认的配置已经适用于大部分场景了,但也会有一些场景需要自定义日志的场景,我们可能过logger.add()方法来实现。

1.3.3.2.1 自定义format

    通过format可以自定义想要输出的内容,而不必输出其他额外的信息,示例如下所示:

import sys
from loguru import loggerdef print_log():logger.info("~~"*30)logger.info("这是一条INFO信息")logger.debug("这是一条DEBUG信息")logger.warning("这是一条WARNING信息")logger.error("这是一条ERROR信息")logger.critical("这是一条CRITICAL信息")logger.trace("这是一条TRACE信息")if __name__ == '__main__':logger.remove()# 修改日志最小级别handler_id=logger.add(sys.stderr,level="INFO",format="{message}")logger.info(f"handler id:{handler_id}")print_log()logger.remove(handler_id)

    输出结果如下所示:

handler id:1
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
这是一条INFO信息
这是一条WARNING信息
这是一条ERROR信息
这是一条CRITICAL信息

    在上述代码中,使用{message}占位符来表示要输出的日志消息。这样我们就得到了一个最小日志输出记录,而无其他额外日志记录,例如时间戳、日志级别、来源等信息。format还支持以下占位符:

  • {time}: 时间戳
  • {level}: 日志级别
  • {message}: 实际的日志消息
  • {name}: Module 名称
  • {line}: 行号

更多占位符的文档可查看官网文档:https://loguru.readthedocs.io/en/stable/api/logger.html#record

    在日常使用,为了更好的进行问题定位和分析日志,在日志记录中,至少包含时间戳日志级别日志内容这三项。示例如下所示:

import sys
from loguru import loggerdef print_log():logger.info("~~"*30)logger.info("这是一条INFO信息")logger.debug("这是一条DEBUG信息")logger.warning("这是一条WARNING信息")logger.error("这是一条ERROR信息")logger.critical("这是一条CRITICAL信息")logger.trace("这是一条TRACE信息")if __name__ == '__main__':logger.remove()# 修改日志最小级别handler_id=logger.add(sys.stderr,level="INFO",format="{time:YYYY-MM-DD HH:mm:ss} | {level} | {message}")logger.info(f"handler id:{handler_id}")print_log()

    输出结果如下所示:

2025-09-27 18:29:40 | INFO | handler id:1
2025-09-27 18:29:40 | INFO | ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
2025-09-27 18:29:40 | INFO | 这是一条INFO信息
2025-09-27 18:29:40 | WARNING | 这是一条WARNING信息
2025-09-27 18:29:40 | ERROR | 这是一条ERROR信息
2025-09-27 18:29:40 | CRITICAL | 这是一条CRITICAL信息

其中时间格式自定义可参考文档: https://loguru.readthedocs.io/en/stable/api/logger.html

    loguru 也支持在format中使用颜色标记符来自定义输出的字符串颜色,例如<red><blue>等。这样在终端中显示日志消息,会自动转换对应的颜色进行显示。示例如下所示:

import sys
from loguru import loggerdef print_log():logger.info("~~"*30)logger.info("这是一条INFO信息")logger.debug("这是一条DEBUG信息")logger.warning("这是一条WARNING信息")logger.error("这是一条ERROR信息")logger.critical("这是一条CRITICAL信息")logger.trace("这是一条TRACE信息")if __name__ == '__main__':logger.remove()# 修改日志最小级别handler_id=logger.add(sys.stderr,level="INFO",format="<red><b>{time:YYYY-MM-DD HH:mm:ss}</b></red> | <blue>{name}:{line}</blue> | <green>{level}</green> | <yellow><b> {message} </b></yellow>")logger.info(f"handler id:{handler_id}")print_log()

    输出结果如下所示:

04-自家义format颜色.png

1.3.3.2.2 添加日志上下文

    在一部分场景中,我们可以添加一些额外的上下文信息,来帮助更好理解在记录日志时发生了什么事情。loguru也提供几种方式来添加上下文信息。其中最简单常见的方式,就是通过关键字参数来传值。示例如下所示:

import sys
from loguru import loggerif __name__ == '__main__':logger.remove()# 修改日志最小级别handler_id=logger.add(sys.stderr,level="INFO",format="{time:YYYY-MM-DD HH:mm:ss}| {level} | {message} | {extra}")logger.warning(f"日志级别为警告级别", log_level="WARNING")logger.info(f"handler id:",handler_id=handler_id)

    输出结果如下所示:

2025-09-27 18:55:58| WARNING | 日志级别为警告级别 | {'log_level': 'WARNING'}
2025-09-27 18:55:58| INFO | handler id: | {'handler_id': 1}

    上述通过占位符{extra}为日志添加了一个上下文信息,适合于一次性添加的场景,loguru 还提供了以下两个方法,来适用更多的场景:

  • bind(): 可以在所有handler实例上面添加额外的上下文信息,属于永久性添加
  • contextualize(): 添加临时性的上下文信息

    bind()方法非常适合于在所有的logger实例中添加额外的上下文信息。例如,在所有logger实例上添加诸如userId、sessionIdt。这种操作将大量节省在所有logger上手动添加额外上下文信息。示例代码如下所示:

import sys
from loguru import loggerif __name__ == '__main__':logger.remove()# 修改日志最小级别handler_id=logger.add(sys.stderr,level="INFO",format="{time:YYYY-MM-DD HH:mm:ss}| {level} | {message} | {extra}")user_logger=logger.bind(username="Surpass",user_id=999,session_id=8888)user_logger.info("I am Supass")user_logger.warning("loguru user logger.bind()")

    输出结果如下所示:

2025-09-27 19:09:50| INFO | I am Supass | {'username': 'Surpass', 'user_id': 999, 'session_id': 8888}
2025-09-27 19:09:50| WARNING | loguru user logger.bind() | {'username': 'Surpass', 'user_id': 999, 'session_id': 8888}

    contextualize()提供了一种非常干净的方式来添加一个临时的上下文信息,而且在操作完成后还会自动清理,示例代码如下所示:

import sys
from loguru import loggerif __name__ == '__main__':logger.remove()# 修改日志最小级别handler_id=logger.add(sys.stderr,level="INFO",format="{time:YYYY-MM-DD HH:mm:ss}| {level} | {message} | {extra}")with logger.contextualize(username="Surpass",user_id=999,session_id=8888):logger.info("Add temporarily context with contextualize")logger.warning("Hello Surpass",without_contextualize=True)

    在上述示例中,contextualize()事实上使用了Python的上下文管理器来临时添加额外的上下文信息,在with块里面,所有日志消息都会被添加额外的上下文信息,而一旦退出with块,则额外的上下文信息则会移除。

    输出结果如下所示:

2025-09-27 19:16:55| INFO | Add temporarily context with contextualize | {'username': 'Surpass', 'user_id': 999, 'session_id': 8888}
2025-09-27 19:16:55| WARNING | Hello Surpass | {'without_contextualize': True}
1.3.3.2.3 保存日志到文件

    将日志输出到终端在开发阶段非常有用,而在生产环境中,日志需要保存到文件中,供日后的问题定位和日志分析。loguru 允许将日志保存至文件,并设置日志切割日志保留期限策略。

  • Log rotation: 即日志切割,它通常决定在什么时候开启一个新的文件用于记录日志,可以由日志文件大小时间间隔其他条件等决定。支持以下几种方式的定义:
    文件大小: 当文件大小达到设定的大小后,创建新的日志文件,可以取的值有:100 MB2 GB
    时间: 即达到指定的时间就创建新的日志文件,可以取的值有:12:00
    时间间隔:即达到指定的时间间隔之后,就创建新的日志文件,可以取的值有: 12 hours3 days

  • Log retention: 即日志保留期限,它通常决定何时删除旧的日志文件,可以由基于数量基于时间来决定。支持以下几种方式的定义:
    基于数量: 即仅保留最近n个文件,如果设置为3,则表示仅保留最近3个日志文件,其他日志文件则删除
    基于时间:即仅保留最近设定时间的文件,如果设置为"1 week",则表示仅保留最近1雕的日志文件,其他日志文件则删除

from loguru import loggerif __name__ == '__main__':logger.remove()# 修改日志最小级别handler_id=logger.add("app.log",level="INFO",format="{time:YYYY-MM-DD HH:mm:ss}| {level} | {message} | {extra}",rotation="1 KB", # 即日志文件达到1KB,就创建一个新日志文件retention="1d"   # 即日志文件仅保留当天,其他则要删除)with logger.contextualize(username="Surpass",user_id=999,session_id=8888):logger.info("Add temporarily context with contextualize")logger.warning("Hello Surpass",without_contextualize=True)
1.3.3.2.4 错误处理和使用Loguru调试

    当我们在调试程序时,仅仅从日志中得知程序运行出现错误信息是不够的。我们需要知道错误是什么时候产生和为什么会产生错误等。loguru 提供了一个非常强大的功能来辅助查看详细的日志信息,例如错误信息、变量信息、上下文信息等。

  • 使用装饰器@logger.catch

    最简单抓取错误日志信息的方式就是使用装饰器@logger.catch。示例如下所示:

import sys
from loguru import logger@logger.catch
def divide(a:int,b:int)->int:return a/bif __name__ == '__main__':divide(10,0)

    上述代码在运行会出现报错,loguru产生的日志如下所示:

2025-09-27 20:06:45.140 | ERROR    | __main__:<module>:10 - An error has been caught in function '<module>', process 'MainProcess' (4288), thread 'MainThread' (24912):
Traceback (most recent call last):> File "C:\Users\Surpass\Documents\PyCharmProjects\TestNote\test-note\loguru-demo\main.py", line 10, in <module>divide(10,0)└ <function divide at 0x000001EE6B0C8860>File "C:\Users\Surpass\Documents\PyCharmProjects\TestNote\test-note\loguru-demo\main.py", line 6, in dividereturn a/b│ └ 0└ 10ZeroDivisionError: division by zero
  • 使用装饰器@logger.catch并添加其他额外信息

    使用基本装饰器@logger.catch可以做到不需要任何配置就能自动捕捉错误信息,但在一些大型工程中,我们通常需要自行处理和控制输出的错误信息,这个时候就需要能够自定义一些错误信息、日志级别、处理特定类型的错误。这个时候我们依然可以使用装饰器@logger.catch,并传递额外的参数即可。示例如下所示:

import sys
from loguru import logger@logger.catch(message="database connection failed",level="ERROR")
def connect_to_db(addr:str,port:int):if port < 1000:raise ValueError("Port must be greater than 1000")# 模拟连接数据库错误raise Exception("Connection to database failed")if __name__ == '__main__':connect_to_db("127.0.0.1",123)

    输出结果如下所示:

2025-09-27 20:18:06.998 | ERROR    | __main__:<module>:12 - database connection failed
Traceback (most recent call last):> File "C:\Users\Surpass\Documents\PyCharmProjects\TestNote\test-note\loguru-demo\main.py", line 12, in <module>connect_to_db("127.0.0.1",123)└ <function connect_to_db at 0x00000249B8400400>File "C:\Users\Surpass\Documents\PyCharmProjects\TestNote\test-note\loguru-demo\main.py", line 7, in connect_to_dbraise ValueError("Port must be greater than 1000")ValueError: Port must be greater than 1000
1.3.3.2.5 文件和控制台同时输出日志

    在前面的示例中,日志要么输出到文件,要么输出到控制台,现在想同时输出到文件和控制中,该如何操作了,示例代码如下所示:

import sys
from loguru import loggerformat="<green>{time:YYYY-MM-DD HH:mm:ss ZZ}</green> | <red><b>{level}</b></red> | <blue>{message}</blue> | {extra}"
level="DEBUG"config={"handlers": [{"sink":sys.stdout,"format":format,"level":level},{"sink":"app.log", "format":format,"level":level}],"extra": {"name":"Surpass"}
}logger.configure(**config)logger.info(logger.level(level))
logger.info("I am Surpass",level="INFO",age=28)
logger.warning("Test Warning",level="WARNING")
logger.debug("Test Debug",level="DEBUG")
logger.error("Test Error",level="ERROR")

    输出结果如下所示:

2025-09-27 21:28:22 +0800 | INFO | Level(name='DEBUG', no=10, color='<blue><bold>', icon='🐞') | {'name': 'Surpass'}
2025-09-27 21:28:22 +0800 | INFO | I am Surpass | {'name': 'Surpass', 'level': 'INFO', 'age': 28}
2025-09-27 21:28:22 +0800 | WARNING | Test Warning | {'name': 'Surpass', 'level': 'WARNING'}
2025-09-27 21:28:22 +0800 | DEBUG | Test Debug | {'name': 'Surpass', 'level': 'DEBUG'}
2025-09-27 21:28:22 +0800 | ERROR | Test Error | {'name': 'Surpass', 'level': 'ERROR'}

2.参考资料

  • https://github.com/Delgan/loguru
  • https://loguru.readthedocs.io/en/stable/index.html
  • https://realpython.com/python-loguru/

本文同步在微信订阅号上发布,如各位小伙伴们喜欢我的文章,也可以关注我的微信订阅号:woaitest,或扫描下面的二维码添加关注:

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/919990.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

MATLAB工具箱

MATLAB工具箱一、一维离散数据微分、积分求解 1. 离散积分 function result = integral(x,y,c)result = [];for i=1:1:length(y)c=y(i)*(x(2)-x(1))+c ; result(end+1) = c;end end2. 离散微分 function result = diff…

内存访问流程

*假设执行 int a=0x1234(分配一块逻辑地址,0x56789999)32位系统 *CPU会将逻辑地址拆分为两部分 V=56789() 页内偏移=0x999 *由MMU使用0x56789变量,查进程表找到值为0xabcde *拼接物理地址:0xabcde 999 *有内存…

网站推广洛阳wordpress插件中文版下载

C# 中的字符串类型&#xff08;string&#xff09;是不可变的&#xff0c;这意味着一旦创建了一个字符串对象&#xff0c;就不能再对其进行修改。 当对一个字符串进行拼接、替换、删除等操作时&#xff0c;实际上是创建了一个新的字符串对象&#xff0c;而原始的字符串对象保持…

.NET操作Word实现智能文档处理 - 内容查找替换与书签操作

如何在Word大量文档中查找并替换特定内容?如何在文档的特定位置自动插入动态内容?如何创建能够自动生成报告的智能文档系统?本文介绍的查找替换和书签操作技术,将能够轻松实现这些功能,大大提高文档处理的效率和准…

day19_添加 修改

day19_添加 修改 1添加场景分析1使用弹出框 承载添加界面 2弹出框输入菜单信息 提交到添加接口 3添加接口处理完毕 反馈信息 弹窗处理结果 关闭弹出框 刷新table数据 2sql分析 -- 逻辑主键 一般不加自增 由使用人员维…

day18_查询功能 合并servlet

day18_查询功能 合并servlet 1.sql分析 -- 分页+条件 查询 select am1.*,IFNULL(am2.menuname,无) as pname from admin_menu am1 left join admin_menu am2 on am1.pid = am2.mid-- 动态查询条件 where am1.menuna…

NOIP模拟赛 十七

倍增+DP+DP+可持久化平衡树A. 对于一个 \(x\) ,如果 \(x\bmod a < x\) ,称其为有效的。我们断言,有效次取模只会发生 \(\log\) 次。 如果发生有效取模,则 \(a<x\) 。\(a\le \frac{x}{2}\) 则 \(x\bmod a <…

day22_用户模块

day22_用户模块 1查询sql分析 -- 定制系统 -- 查询分段记录 select au1.*,au2.username create_uname from admin_user au1 left join admin_user au2 on au1.create_uid = au2.uidwhere au1.username like CONCAT(%,a…

做招聘网站多少钱网站找不到首页

一切从“/”开始 在Linux系统中&#xff0c;目录、字符设备、块设备、套接字、打印机等都被抽象成了文件&#xff0c;一切皆为件 与windows操作系统不同&#xff0c;Linux系统内不存在C/D/E/F盘等&#xff0c;一切文件都是从根&#xff08;/&#xff09;目录开始的 Linux系统…

常州网站建设要多少钱wordpress 全站ajax

随着物联网、大数据、人工智能等技术的快速发展&#xff0c;边缘计算已成为当前信息技术领域的一个热门话题。在物联网领域&#xff0c;边缘计算被广泛应用于智慧交通、智能安防、工业等多个领域。因此&#xff0c;基于边缘计算技术的工业主板设计方案也受到越来越多人的关注。…

2025 丹东店推荐:丽格门窗,用 20 年技术沉淀守护家的舒适

在四季分明、冬季严寒的丹东,门窗的隔热保温、密封抗风性能直接决定着家居生活的幸福感。2025 年装修选门窗,坐落于丹东市振兴区兴六路大昌建材隔壁的丽格门窗店,带来了专为北方气候定制的系统门窗解决方案,其深厚…

NOIP2025模拟赛23

T1 T2 T3 T4\(\color{#52C41A} 普及+/提高\) \(\color{#3498DB} 提高+/省选-\) \(\color{#52C41A} 普及+/提高\) \(\color{#9D3DCF} 省选/NOI-\)参赛网址:https://oj.33dai.cn/d/TYOI/contest/689d2670c5d9c2f14c2250…

step

action被输入到机器人的控制器之前,做一个预处理,做一个clip截断,乘以一个scale,做完之后,再apply到机器人,计算reward和done(超时或者terminate),有done就reset,apply interval event,最后计算观测。 acti…

2025 呼和浩特店推荐:丽格门窗,用 20 年技术沉淀守护家的温度

在呼和浩特寒冷漫长的冬季与多风的气候环境中,门窗的隔热保温、抗风压性能直接决定着居住的舒适度与能耗成本。2025 年装修选门窗,位于呼和浩特市新城区欧亚达家具一楼的丽格门窗,凭借二十余年系统门窗专业积淀与针…

深入解析:浏览器端音视频处理新选择:Mediabunny 让 Web 媒体开发飞起来

深入解析:浏览器端音视频处理新选择:Mediabunny 让 Web 媒体开发飞起来pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; display: block !important; font-family:…

2025 宁波门窗店推荐:丽格门窗,甬城品质家居的安心之选

在宁波四季分明且湿润多雨的气候下,门窗的隔热、防水、隔音性能直接决定居家舒适度。2025 年装修或换窗,位于宁波市鄞州区宁穿路 988 号筑入空间 2 楼北侧的丽格门窗,凭借 20 余年系统门窗专业积淀与针对性产品设计…

移动硬盘上的文件消失了?以下是Mac电脑解除方法

pre { white-space: pre !important; word-wrap: normal !important; overflow-x: auto !important; display: block !important; font-family: "Consolas", "Monaco", "Courier New", …

2025 贵阳门窗店优选:丽格门窗,用 20 年匠心适配高原宜居需求

在 2025 年的贵阳门窗市场,若想挑选兼具品质与适配性的系统门窗,位于贵阳市北京西路云岩区红星美凯龙中后庭 4 楼的丽格门窗绝对值得优先考量。作为深耕系统门窗领域 20 余载的知名品牌,丽格门窗凭借全产业链实力与…

2025 济南门窗店选购指南:丽格门窗凭硬实力圈粉品质家庭

在 2025 年济南门窗市场消费升级浪潮中,越来越多业主将性能优先、品质可控、环保节能作为选购核心标准。深耕系统门窗领域 20 余年的丽格门窗,凭借全产业链优势与硬核产品力,成为济南改善型住房与品质家装的优选品牌…

移动wap站点京东云建站

一个隐形的九宫格 规划的内容 根据前面关于因子分析、知识表征和结构特征等个方面和智能聊天工具的沟通和分析&#xff0c;我重新梳理了一下&#xff0c;对全量知识系统运营的组织结构及其组织层次和组织模式 的设计&#xff0c;得出一个大致的内容框架。如下&#xff1a; 知…