Python中的字符串比较:是vs==

Python中的字符串比较:是vs==,python,string,comparison,equality,Python,String,Comparison,Equality,我注意到我正在编写的一个Python脚本运行异常,并将其跟踪到一个无限循环,其中循环条件为,而行不是“”。在调试器中运行它,结果表明该行实际上是'。当我把它改成!=''时而不是不是“”,它工作正常 此外,即使在比较int或Boolean值时,通常也认为默认情况下使用“==”更好吗?我一直喜欢使用“是”,因为我觉得它更美观,更像蟒蛇(这就是我落入这个陷阱的原因…),但我想知道它是否只是为了当你想找到两个具有相同id的对象时才使用的。参见 你的阅读逻辑 对于所有内置Python对象(如 字符串、列表

我注意到我正在编写的一个Python脚本运行异常,并将其跟踪到一个无限循环,其中循环条件为
,而行不是“”
。在调试器中运行它,结果表明该行实际上是
'
。当我把它改成
!=''时而不是
不是“”
,它工作正常

此外,即使在比较int或Boolean值时,通常也认为默认情况下使用“==”更好吗?我一直喜欢使用“是”,因为我觉得它更美观,更像蟒蛇(这就是我落入这个陷阱的原因…),但我想知道它是否只是为了当你想找到两个具有相同id的对象时才使用的。

参见

你的阅读逻辑

对于所有内置Python对象(如 字符串、列表、命令、函数、, 等等),如果x是y,那么x==y也是 对

有点瑕疵

如果
应用,则
=
将为真,但它不会反过来应用
=
可能产生True,而
则产生False

对于所有内置Python对象(如 字符串、列表、命令、函数、, 等等),如果x是y,那么x==y也是 对

不总是这样。南是一个反例。但通常,身份(
)意味着平等(
=
)。反之亦然:两个不同的对象可以具有相同的值

此外,通常认为默认情况下使用“==”更好吗 比较int或Boolean值时

比较值时使用
=
,比较标识时使用
is

在比较int(或通常的不可变类型)时,您几乎总是想要前者。有一种优化方法允许将小整数与
is
进行比较,但不要依赖它

对于布尔值,根本不应该进行比较。而不是:

if x == True:
    # do something
写:

if x:
    # do something
None
相比,
为None
优于
==None

我一直喜欢用“是”,因为 我觉得它更美观 和pythonic(我就是这样陷入其中的) 这个陷阱…,但我不知道是不是 打算只留到什么时候 你关心的是找到两个物体 使用相同的id


是的,这正是它的目的。

我想展示一个小例子,说明
是如何与不可变类型相关的。试试看:

a = 19998989890
b = 19998989889 +1
>>> a is b
False
>>> a == b
True
is
比较内存中的两个对象,
==
比较它们的值。例如,您可以看到Python缓存了小整数:

c = 1
b = 1
>>> b is c
True

比较值时应使用
=
,比较标识时应使用
is
。(同样,从英语的角度来看,“equals”与“is”是不同的)

逻辑没有缺陷。声明

如果x是y,那么x==y也是真的

永远不应该被理解为

如果x==y,那么x就是y


读者认为逻辑陈述的相反是真的,这是一种逻辑错误。请参见

@Coquelicot:这不起作用,因为Python允许将任何内容用作布尔表达式。如果你有bool_a==3和bool_b==4,那么bool_a!=bool_b,但是bool_a xor bool_b是假的(因为这两个词都是真的)。@Mike:
x是x
总是真的。但这并不意味着
x==x
。NaN被定义为不等于它本身。关于速度,我认为检查一个字符串是否被修改(例如,从re.sub返回的结果)比较大字符串的
相等,而不是
=
会更快。这几乎是事实,但它的速度仅提高了0.4%。在我的例子中,将来re.sub开始更改字符串的风险是不值得的。对于多年后研究这个问题的人来说,Python 3仍然是这样。@beauxq:Try
nan=float('nan');楠是楠;nan==nan
意味着
==
只对内置类型必须为真。我们可以很容易地编写一个对象本身不相等的类。通过说“如果
应用,那么
=
将是真的,但它不会反过来应用。”您只是说明OP观察到的内容。另一个简单的示例,
datetime.date.today()==datetime.date.today()
==>True,但
datetime.date.today是datetime.date.today()
==>False,因为它们是等效的日期对象,但仍然是不同的对象。您的建议避免的另一个危险示例是:
str(None)是“None”
计算结果为
False
str(None)=='None'
计算结果为
True
这里有一个带字符串的:
x='foo';y='bar'。替换为('bar','foo');(x是y)=False
我喜欢的另一个例子:“a'*50=='a'*50(返回True),而'a'*50是'a'*50(返回False)这与你的经验有什么关系?”?NaN是唯一内置的反例;你只是误解了方向关系。规范说“对于所有内置Python对象(如字符串、列表、dict、函数等),如果x是y,那么x==y也是真的。”,而不是“对于所有内置Python对象(如字符串、列表、dict、函数等),如果x==y,那么x是y也是真的。”出于某种原因,你假装它说的是后者。没有。你可以看到相等匹配,但不匹配。前一份引述的声明完全允许了这一点。我对那篇文章的理解完全混乱了。我编辑它是不可能的,因为我不认为它对未来的读者有用。o1是o2=>比较o1和o2是否都指向内存中相同的物理位置(换句话说,如果它们是相同的对象)。而o1==o2=>在这里,python调用o1的_cmp__(o2)方法,理想情况下,该方法应该比较值并返回True或False。(换句话说,它比较值)对于JAVA人员:在JAVA中,确定两个字符串变量