【问题标题】:Python 2 vs Python 3 - Difference in map behavior with three arguments?Python 2 vs Python 3 - 三个参数的地图行为差异?
【发布时间】:2020-03-04 18:37:17
【问题描述】:

以下代码在 Python 2 和 Python 3 中的行为不同:

all(map(lambda x,y: x, [1, 2], [1, 2, 3]))

Python 2 给出 False 而 Python 3 给出 True。 Python 2 的 documentation 表示,如果较短的列表用完,它将提供 None,但 Python 3 doesn't 会这样做。

我正在编写一个出于某种原因确实需要保持长度的代码。获得旧行为的最干净的方法是什么?我知道我可以使用from past.builtin import map as old_map,但是有没有更优雅的解决方案可以同时在这两个版本中使用?

【问题讨论】:

  • 你能重写代码吗?或许不使用不同的结构就将该功能放在一个函数中?
  • 为什么不为此使用自己的自定义函数?
  • @JoachimLusiardi 这是一个使用频率很高的小程序...所以我想尽量减少更改。
  • @mrzrm,那我可以用from past.builtin import map :-)
  • 您的示例中有多少细节与您的实际操作相匹配?因为len(list_1) >= len(list_2) and all(list_1) 似乎是一种更好的方法来解决您显示的特定问题,而不会弄乱map 的向后兼容版本或任何替代版本(如itertools.zip_longest)。

标签: python python-3.x python-2.x


【解决方案1】:

本质上,带有多个可迭代参数的map 将zip 迭代,然后使用来自zip 的元组作为var-args 调用函数。因此,您可以使用 itertools.starmap 和 zip 获得相同的行为:

>>> a = [10, 20]
>>> b = [1, 2, 3]
>>> f = lambda x, y: x
>>> list(map(f, a, b))
[10, 20]
>>> from itertools import starmap
>>> list(starmap(f, zip(a, b)))
[10, 20]

那么你想要的行为可以通过将zip替换为itertools.zip_longest来实现:

>>> from itertools import starmap, zip_longest
>>> list(starmap(f, zip_longest(a, b)))
[10, 20, None]

itertools 中的两个函数也存在于 Python 2 中,除了第二个函数被命名为 izip_longest。你可以import ... as ... 来解决这个问题。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-06-03
    • 1970-01-01
    • 1970-01-01
    • 2011-11-07
    • 1970-01-01
    • 1970-01-01
    • 2018-05-11
    • 2015-03-21
    相关资源
    最近更新 更多