Python:为什么不支持列表和元组之间的比较?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/2345092/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-04 00:23:56  来源:igfitidea点击:

Python: Why is comparison between lists and tuples not supported?

pythonlistcomparisontuples

提问by AndiDog

When comparing a tuple with a list like ...

将元组与列表进行比较时...

>>> [1,2,3] == (1,2,3)
False
>>> [1,2,3].__eq__((1,2,3))
NotImplemented
>>> (1,2,3).__eq__([1,2,3])
NotImplemented

... Python does not deep-compare them as done with (1,2,3) == (1,2,3).

... Python 不会像使用(1,2,3) == (1,2,3).

So what is the reason for this? Is it because the mutable list can be changed at any time (thread-safety issues) or what?

那么这是什么原因呢?是因为可变列表可以随时更改(线程安全问题)还是什么?

(I know where this is implemented in CPython, so please don't answer where, but whyit is implemented.)

(我知道这是在 CPython 中实现的,所以请不要回答where,而是为什么要实现它。)

回答by Esteban Küber

You can always "cast" it

你总是可以“投射”它

>>> tuple([1, 2]) == (1, 2)
True

Keep in mind that Python, unlike for example Javascript, is stronglytyped, and some (most?) of us prefer it that way.

请记住,Python 与 Javascript 不同,它是强类型的,我们中的一些(大多数?)更喜欢这种方式。

回答by Chris B.

There's no technical reason for lists not being able to compare to tuples; it's entirely a design decision driven by semantics. For proof that it's not related to thread-safety, you can compare lists to other lists:

列表无法与元组进行比较没有技术原因;这完全是由语义驱动的设计决策。为了证明它与线程安全无关,您可以将列表与其他列表进行比较:

>>> l1 = [1, 2, 3]
>>> l2 = [1, 2, 3]
>>> l1 == l2
True
>>> id(l1) == id(l2)
False

It seems reasonable to allow users to directly compare lists and tuples, but then you end up with other questions: should the user be allowed to compare lists and queues? What about any two objects which provide iterators? What about the following?

允许用户直接比较列表和元组似乎是合理的,但是你最终会遇到其他问题:是否应该允许用户比较列表和队列?任何两个提供迭代器的对象呢?下面呢?

>>> s = set([('x', 1), ('y', 2)])
>>> d = dict(s)
>>> s == d  # This doesn't work
False

It can get complicated pretty quickly. The language designers recognized the issue, and avoided it by simply preventing different collection types from comparing directly with each other1.

它会很快变得复杂。语言设计者认识到了这个问题,并通过简单地防止不同的集合类型相互直接比较来避免它1

Note that the simple solution (to create a new list from the tuple and compare them) is easy but inefficient. If you're working with large numbers of items, you're better off with something like:

请注意,简单的解决方案(从元组创建一个新列表并比较它们)很容易但效率低下。如果您正在处理大量项目,则最好使用以下内容:

def compare_sequences(iter1, iter2):
    iter1, iter2 = iter(iter1), iter(iter2)
    for i1 in iter1:
        try:
            i2 = next(iter2)
        except StopIteration:
            return False

        if i1 != i2:
            return False

    try:
        i2 = next(iter2)
    except StopIteration:
        return True

    return False

This has the advantage of working on any two sequences, at an obvious cost in complexity.

这具有处理任何两个序列的优势,但显然会增加复杂性。



1I note there's an exception for sets and frozensets. And no doubt a few others I'm not aware of. The language designers are purists, except where it pays to be practical.

1我注意到集合和冻结集有一个例外。毫无疑问,还有一些我不知道的。语言设计者是纯粹主义者,除了实用的地方。