Mar*_*nen 12 python string string-formatting python-3.x
我看到"为什么不join()自动将其参数转换为字符串?" 和接受的答案让我思考:既然
显式优于隐式.
和
错误不应该默默地传递.
为什么str.format()忽略额外/未使用(有时是意外传递)的参数?对我来说,它看起来像是一个无声地传递的错误,它肯定不是明确的:
>>> 'abc'.format(21, 3, 'abc', object(), x=5, y=[1, 2, 3])
'abc'
Run Code Online (Sandbox Code Playgroud)
其实,这导致我的朋友一个问题与os.makedirs(path, exist_ok=True)仍然引发错误,即使该文档os.makedirs()称,exist_ok=True即使不会引发错误path已经存在.原来他只是有一个嵌套函数调用的长行,并且exist_ok被传递到嵌套.format()调用而不是os.makedirs().
Mar*_*ers 13
忽略未使用的参数可以为任意大小的字典或对象创建任意格式字符串.
假设您希望为程序提供让最终用户更改输出的功能.您可以记录哪些字段可用,并告诉用户将这些字段放在{...}字符串的插槽中.然后,最终用户可以使用任意数量的字段创建模板字符串,包括根本不包含任何字段,没有错误.
换句话说,选择是有意的,因为允许更多参数而不是转换的实际原因.请注意String.Formatter,出于同样的原因,启发Python PEP 的C#实现也是如此.
并非PEP这一部分的讨论是明确的; Guido van Rossum在某些时候试图解决这个问题:
如果位置参数太少或太多,或者关键字丢失或未使用,PEP会对发生的情况保持沉默.遗失的应该是错误; 我不确定冗余(未使用)的那些.一方面抱怨这些让我们更加确定格式字符串是正确的.另一方面,有一些用于传递大量关键字参数的用例(例如,简单的网页模板可以使用**dict传递一组固定的变量).即使在i18n(翻译)应用程序中,我也可以看到允许未使用参数的有用性
PEP作者回答说他们在这一点上仍未决定.
对于必须为未使用的参数引发异常的用例,您应该为string.Formatter()该类创建子类并为其提供实现Formatter.check_unused_args(); 默认实现什么都不做.这当然不会帮助你朋友的情况str.format(*args, **kwargs)而不是你使用的情况Formatter().format(str, *args, **kwargs).我相信在某些时候,我们的想法是你可以用str.format()自定义实现替换使用的格式化程序,但这种情况从未发生过.
如果你使用flake8linter,那么你可以添加flake8-string-format插件来检测明显的情况,你传入一个未被格式字符串使用的显式关键字参数.