如何使用python-3.x中的字典格式化字符串?

如何使用python-3.x中的字典格式化字符串?,python,string,dictionary,python-3.x,Python,String,Dictionary,Python 3.x,我非常喜欢使用字典格式化字符串。它可以帮助我阅读我正在使用的字符串格式,还可以让我利用现有的字典。例如: class MyClass: def __init__(self): self.title = 'Title' a = MyClass() print 'The title is %(title)s' % a.__dict__ path = '/path/to/a/file' print 'You put your file here: %(path)s' % l

我非常喜欢使用字典格式化字符串。它可以帮助我阅读我正在使用的字符串格式,还可以让我利用现有的字典。例如:

class MyClass:
    def __init__(self):
        self.title = 'Title'

a = MyClass()
print 'The title is %(title)s' % a.__dict__

path = '/path/to/a/file'
print 'You put your file here: %(path)s' % locals()
但是,我无法理解Python3.x语法是否可以执行相同的操作(或者如果可能的话)。我想做以下几件事

# Fails, KeyError 'latitude'
geopoint = {'latitude':41.123,'longitude':71.091}
print '{latitude} {longitude}'.format(geopoint)

# Succeeds
print '{latitude} {longitude}'.format(latitude=41.123,longitude=71.091)

要将字典解压为关键字参数,请使用
**
。此外,新样式格式支持引用对象属性和映射项:

'{0[latitude]} {0[longitude]}'.format(geopoint)
'The title is {0.title}s'.format(a) # the a from your first example
这对你有好处吗

geopoint = {'latitude':41.123,'longitude':71.091}
print('{latitude} {longitude}'.format(**geopoint))

Python 2语法也适用于Python 3:

>>> class MyClass:
...     def __init__(self):
...         self.title = 'Title'
... 
>>> a = MyClass()
>>> print('The title is %(title)s' % a.__dict__)
The title is Title
>>> 
>>> path = '/path/to/a/file'
>>> print('You put your file here: %(path)s' % locals())
You put your file here: /path/to/a/file

由于Python 3.0和3.1已经过时,没有人使用它们,因此您可以也应该使用(Python 3.2+):

类似于
str.format(**mapping)
除了直接使用映射,而不是复制到
dict
。例如,如果映射是一个
dict
子类,这将非常有用

这意味着您可以使用例如
defaultdict
,为缺少的键设置(并返回)默认值:

>>> from collections import defaultdict
>>> vals = defaultdict(lambda: '<unset>', {'bar': 'baz'})
>>> 'foo is {foo} and bar is {bar}'.format_map(vals)
'foo is <unset> and bar is baz'
然后

约为10纳秒(2%),比

>>> 'foo is {foo}, bar is {bar} and baz is {baz}'.format(**d)
在我的Python 3.4.3上。当字典中有更多的键时,差异可能会更大,并且


请注意,格式语言比这灵活得多;它们可以包含索引表达式、属性访问等,因此可以格式化整个对象或其中的两个:

>>> p1 = {'latitude':41.123,'longitude':71.091}
>>> p2 = {'latitude':56.456,'longitude':23.456}
>>> '{0[latitude]} {0[longitude]} - {1[latitude]} {1[longitude]}'.format(p1, p2)
'41.123 71.091 - 56.456 23.456'

从3.6开始,您也可以使用插值字符串:

>>> f'lat:{p1["latitude"]} lng:{p1["longitude"]}'
'lat:41.123 lng:71.091'

您只需要记住在嵌套引号中使用其他引号字符。这种方法的另一个优点是,它比

快得多,因为问题是特定于Python 3的,这里使用的是自Python 3.6以来就可用的:

>>> geopoint = {'latitude':41.123,'longitude':71.091}
>>> print(f'{geopoint["latitude"]} {geopoint["longitude"]}')
41.123 71.091

注意外部的单引号和内部的双引号(你也可以用另一种方式来做)。

大多数答案只格式化了dict的值

如果要将键格式化为字符串,可以使用dict.items():

输出:

(‘纬度’,41.123)(‘经度’,71.091)

如果要以任意方式格式化,即不显示元组之类的键值:

from functools import reduce
print("{} is {} and {} is {}".format(*reduce((lambda x, y: x + y), [list(item) for item in geopoint.items()])))
输出:

纬度是41.123,经度是71.091


使用format_map执行您想要的操作

print('{latitude} {longitude}'.format_map(geopoint))
这样做的好处是

  • 字典不必放大成参数(与
    **geopoint
    相比)
  • 格式字符串只能访问提供的映射,而不能访问整个变量范围(与F字符串相比)

尝试了这个方法,效果很好。但我不明白“指针符号”的用法。我知道Python不使用指针,这是KWAGS的一个例子吗?@ HuMunCuleReCurLi,它是一个格式参数(最小字段宽度),而不是指针C++风格的指针。介绍了Python 3.2。类似于
str.format(**mapping)
,不同之处在于
mapping
直接使用,而不是复制到
dict
。例如,如果
映射
是一个dict,则此选项非常有用subclass@eugene**对python字典做了什么?我不认为它创建对象是因为print(**geopoint)无法给出语法error@NityeshAgarwal它以名称=值对作为单个参数扩展字典,即
print(**geopoint)
print(经度=71.091,纬度=41.123)
相同。在许多语言中,它被称为splat操作符。在JavaScript中,它被称为扩展运算符。在python中,这个操作符没有特定的名称。很好的一个,相对于
格式
,是否有任何性能改进?(考虑到它没有抄袭到一篇格言中)@BhargavRao不多,2%:D@BhargavRao如果您要寻找性能,请使用此
'%(纬度)s%(经度)s'%geopoint
;)我发现这个答案更好,因为为占位符添加位置索引使代码更显式,更易于使用。特别是如果你有这样的东西:
{0[纬度]}{1[纬度]}{0[经度]}{1[经度]}。格式(geopoint0,geopoint1)
如果您使用的是
defaultdict
并且没有所有的键,那么这将非常有用。我想说的是,f字符串的使用更符合python3方法。请记住,f字符串是python3.6中的新手,而不是3.5中的新手。此外,它的性能也明显高于
f”“
”.format()
;)你错过了一个;)<代码>打印('%(纬度)s%(经度)s'%geopoint)这也比另一个要快得多2@tcll实际上,我想要这些示例,在其中我可以在字符串中使用字典名。类似这样的
“%”(geopoint[“latitude”])s%(geopoint[“longitude”])s“{“geopoint”:geopoint}
注意,
geopoint.items()
;“longitude”可能位于“latitude”之前)谢谢我不知道为什么没有更多的选票。这是最简单的选择,TBH。这也是将列表转换为varargs的类似方法。应该是这样。
>>> geopoint = {'latitude':41.123,'longitude':71.091}
>>> print(f'{geopoint["latitude"]} {geopoint["longitude"]}')
41.123 71.091
geopoint = {'latitude':41.123,'longitude':71.091}
print("{} {}".format(*geopoint.items()))
from functools import reduce
print("{} is {} and {} is {}".format(*reduce((lambda x, y: x + y), [list(item) for item in geopoint.items()])))
geopoint = {'latitude':41.123,'longitude':71.091}

# working examples.
print(f'{geopoint["latitude"]} {geopoint["longitude"]}') # from above answer
print('{geopoint[latitude]} {geopoint[longitude]}'.format(geopoint=geopoint)) # alternate for format method  (including dict name in string).
print('%(latitude)s %(longitude)s'%geopoint) # thanks @tcll
print('{latitude} {longitude}'.format_map(geopoint))