In this post, we will see how to resolve Two list copies has same id
Question:As I know, using “=” for copying objects actually just creates another reference to the same object. So if I do
2367729946880 2367729946880 True, which is fine and obvious.
If I make copies of list, they has different ids:
2646790648192 2646790705984 False.
So far so good. Though, if I try creating copies directly in the print, they unexpectedly has the same id:
How does it happen?
I tried a bunch of different stuff, like:
- assigning copies to variables in the same line in case there is some one-line optimization as Python is an interpreted language
- passing copies to the function to avoid using “=”
- passing copies to the function, using *args because as I know, print() gets arguments same way:
1764444352896 1764444338496(difference in 3rd least valuable digit)
None seem to produce same behaviour. Even comparing ids using operator “is” prints False:
But using “==” still gives True:
Summing up all the text, I wonder about:
- What provokes this kind of behaviour? It doesn’t seem intended. Is it result of some optimization?
- Can it potentially lead to some nasty unexpected bugs? Is there another way to get two copies to have same id?
idreturns an integer that is unique for the lifetime of the object. Here, that
idgot re-used, b ecause the lifetime of the objects did not overlap. In the expression:
a.copy()is evaluated, it creates a new dict, that dict gets passed to
idreturns an integer, the dict is no longer referenced, and immediately reclaimed (this is a Cpython implementation detail). Then,
a.copy()is evaluated again, and again, it is passed to
id. It returns the same
intbecause that is perfectly in-line with the documented function of
id. You can look at the dissasembled bytecode and see how this works exactly:
Another way to see similar behavior:
listobjects, but they were able to re-use the id because they have non-overlapping lifetimes.
So, this is all working as intended and documented.
If you have better answer, please add a comment about this, thank you!