我试图将一个列表映射为十六进制,然后在其他地方使用该列表。在python 2.6中,这很简单:
答:Python 2.6:
>>> map(chr, [66, 53, 0, 94])
['B', '5', '\x00', '^']
然而,在Python 3.1中,上述函数返回一个map对象。
B: Python 3.1:
>>> map(chr, [66, 53, 0, 94])
<map object at 0x00AF5570>
如何在Python 3.x上检索映射列表(如上A所示)?
或者,有没有更好的方法来做这件事?我的初始列表对象有大约45项和id想把它们转换为十六进制。
转换我的旧注释以获得更好的可见性:对于完全没有映射的“更好的方法”,如果您的输入已知是ASCII序数,那么转换为字节和解码通常要快得多,a la bytes(list_of_ordinals).decode(' ASCII ')。这将为您提供值的str,但如果您需要一个列表的可变性或类似的,您可以直接转换它(它仍然更快)。例如,在ipython微基准测试中转换45个输入:
>>> %%timeit -r5 ordinals = list(range(45))
... list(map(chr, ordinals))
...
3.91 µs ± 60.2 ns per loop (mean ± std. dev. of 5 runs, 100000 loops each)
>>> %%timeit -r5 ordinals = list(range(45))
... [*map(chr, ordinals)]
...
3.84 µs ± 219 ns per loop (mean ± std. dev. of 5 runs, 100000 loops each)
>>> %%timeit -r5 ordinals = list(range(45))
... [*bytes(ordinals).decode('ascii')]
...
1.43 µs ± 49.7 ns per loop (mean ± std. dev. of 5 runs, 1000000 loops each)
>>> %%timeit -r5 ordinals = list(range(45))
... bytes(ordinals).decode('ascii')
...
781 ns ± 15.9 ns per loop (mean ± std. dev. of 5 runs, 1000000 loops each)
如果你将其作为str,它将花费最快地图解决方案20%的时间;即使转换回列表,它仍然不到最快地图解决方案的40%。通过bytes和bytes.decode进行批量转换,然后批量转换回list节省了大量工作,但正如所指出的,只有当所有输入都是ASCII序数(或每个字符一个字节的特定区域编码序数,例如latin-1)时才有效。
这样做:
list(map(chr,[66,53,0,94]))
在Python 3+中,许多遍历可迭代对象的进程本身都会返回迭代器。在大多数情况下,这最终会节省内存,并应该使程序运行得更快。
如果你最终要做的只是遍历这个列表,甚至不需要将它转换为列表,因为你仍然可以像这样遍历map对象:
# Prints "ABCD"
for ch in map(chr,[65,66,67,68]):
print(ch)
列表返回映射函数具有节省输入的优点,特别是在交互式会话期间。你可以定义lmap函数(类似于python2的imap),返回list:
lmap = lambda func, *iterable: list(map(func, *iterable))
然后调用lmap而不是map将完成工作:
Lmap (str, x)比list(map(str, x))短5个字符(在本例中为30%),并且肯定比[str(v) for v in x]短。你也可以为filter创建类似的函数。
对最初的问题有一个评论:
我建议重命名为Getting map()以在Python 3中返回一个列表。*因为它适用于所有Python3版本。有办法做到这一点吗?- meawoppl 1月24日17:58
这是可能的,但这是一个非常糟糕的主意。为了好玩,以下是你可以(但不应该)这样做的方法:
__global_map = map #keep reference to the original map
lmap = lambda func, *iterable: list(__global_map(func, *iterable)) # using "map" here will cause infinite recursion
map = lmap
x = [1, 2, 3]
map(str, x) #test
map = __global_map #restore the original map and don't do that again
map(str, x) #iterator