2

So I am getting the following results:

  1. () is () returns True (comparison between two objects)
  2. id(()) is id(()) returns False. (comparison between the representations of object identities)

According to the python documentation:

The ‘is‘ operator compares the identity of two objects; the id() function returns an integer representing its identity.

Given case (1), object () has the same identity (memory address) as object (); but in case (2), the representations of their identities are not identical to each other.

Why is that?

  • So you should compare the `id`s with `id(()) == id(())`... Use `==` not `is`. – Willem Van Onsem Mar 26 '17 at 17:28
  • Because the ids are large integers that exist twice in memory. Only small integers are cached in CPython. – timgeb Mar 26 '17 at 17:32
  • @WillemVanOnsem yeah I understand that the `id()` returns integers but was confused about why they were different *objects* since they are the representations of the same object. –  Mar 26 '17 at 17:38
  • @timgeb good to know. Thanks! –  Mar 26 '17 at 17:38
  • 1
    @timgeb btw, can you add it in the answer below so I can vote it up? thanks! Also, I was curious how large is 'large', and [answers from this question](http://stackoverflow.com/questions/306313/is-operator-behaves-unexpectedly-with-integers) say that anything >256 counts as *large* and anything <=256 is treated as literals –  Mar 26 '17 at 19:41

1 Answers1

1

The id(..) function returns an integer that represents the "identity" of an object so to speak. Although it is true that if two variables x and y refer to the same object, x is y succeed, and the result of id(x) is equal to id(y), that does not mean those integers themeselves are the same object.

You thus should use:

id(()) == id(())
#      ^ == not is

In Python, even ints are objects, and although usually there is a cache such that small integers indeed refer to the same object, the following test will usually fail:

>>> 1234567890 is (1234567891-1)
False
>>> 1234567890 == (1234567891-1)
True
Willem Van Onsem
  • 443,496
  • 30
  • 428
  • 555
  • "and therefore in some cases, the id(..) of an object could change between two calls". I'm fairly sure this is false: it would defeat the whole point of `id`. Do you have any references for this claim? – Mark Dickinson Mar 26 '17 at 17:35
  • 1
    @MarkDickinson: sorry I misread the documentation. The id is indeed guarnateed to be constant during an objects lifetime. (dowside of *speedreading* :( ) – Willem Van Onsem Mar 26 '17 at 17:40
  • 3
    The part about the memory address possibly changing _is_ true, though, for some implementations (e.g., PyPy), which means that PyPy has to jump through hoops to have a constant `id` (which is of course _not_ based on memory addresses). CPython never moves objects around in memory, so using the memory address for the `id` is safe. – Mark Dickinson Mar 26 '17 at 17:42
  • Cool. Thanks for the explanation! –  Mar 26 '17 at 17:44