1. ホーム
  2. python

[解決済み] なぜ(0-6)は-6=偽なのか?重複

2022-07-08 16:45:18

疑問点

重複の可能性があります。

Pythonの "is "演算子は整数で予期せぬ振る舞いをします。

今日、私は自分のプロジェクトをデバッグしようとし、数時間の分析の後、私はこれを得ました。

>>> (0-6) is -6
False

が、しかし

>>> (0-5) is -5
True

なぜなのか、説明していただけませんか? もしかしたら、これは何らかのバグか、非常に奇妙な動作かもしれません。

> Python 2.7.3 (default, Apr 24 2012, 00:00:54) [GCC 4.7.0 20120414 (prerelease)] on linux2
>>> type(0-6) 
<type 'int'>
>>> type(-6) 
<type 'int'>
>>> type((0-6) is -6)
<type 'bool'>
>>> 

どのように解決するのですか?

5 から 256 までのすべての整数は、CPython と同じアドレスを共有するグローバルオブジェクトとしてキャッシュされます。 is のテストはパスします。

このアーティファクトの詳細については http://www.laurentluce.com/posts/python-integer-objects-implementation/ で、現在のソースコードを確認することができます。 http://hg.python.org/cpython/file/tip/Objects/longobject.c .

小さな整数を参照し、共有することでアクセスが高速になるように、特定の構造体が使用されています。これは、整数オブジェクトへの262のポインタの配列です。これらの整数オブジェクトは初期化時に、上で見た整数オブジェクトのブロックに割り当てられています。小整数の範囲は-5から256までです。多くのPythonプログラムはこの範囲の整数を使う時間が長いので、これは賢い判断です。

これはCPythonの実装の詳細に過ぎず、これに依存してはいけません。 例えば PyPy を実装した id は自分自身を返すために整数の (0-6) is -6 は、たとえ内部的に異なるオブジェクトであっても常に真となります。また、この整数キャッシュを有効にするかどうか、さらに下限と上限の設定も可能です。しかし一般に、異なる起源から取得されたオブジェクトは同一ではないでしょう。もし、同一性を比較したいのであれば、単に == .