python assignment

D

dan

without stirring the pot too much --

could someone please point me to whatever documentation exists on the
philosophy, semantics, and practical implications of how Python
implements the assignment operator? So far I can't find much useful
in the regular documentation. I understand the basic concept that
names are bound to objects which exist on the heap, but that still
doesn't explain why a = b doesn't _always_ cause a to point to the
same object as b. What determines when the object in question is
copied? What determines when a future maniplulation of the variable
will cause it to point to an object that is already referenced by
another variable? (see code below for an example).

What I need is an exact and unambiguous algorithm for determining when
an assignment will change the id of the variable (or should I say,
when the evaluation of an expression will cause a new object to be
created). Some of the issues involved can be discerned from the
following session:
True
 
D

dan

Ok, thanks for the responses. I think I 'get' it now. However I do
think it would be an excellent idea to have a bit of exposition on
this subject in the Python tutorial, or perhaps in a separate section.
It's not really hard to understand once you realize what's going on,
but I suspect it causes no end of confusion for both new programmers
and old (those used to langs such as C++).

Here's a better example of how a newbie can get confused:
a = (1,2) #a is a tuple
b = a #b & a now point to same object on heap
a += (3,) #tuples are immutable so += returns a new one
b == a #b points to old, a points to new False
a = [1,2] #a is a list
b = a #a & b point to same object again
a += [3] #a is mutable, so += mutates it
b == a #of course True
a = a + [4] #hmm... one *might* think this is eqiv. to a += [4]
a == b False #but NOOO!!
a [1, 2, 3, 4]
b
[1, 2, 3]

Now that I understand what's happening, it makes sense, but initially
this sort of behavior was quite mysterious.

-dbm
 
J

Juha Autero

Tim Peters said:
It would be very unusual (because bad design) for the __iadd__
method of a mutable type to return a pre-existing object, though.

I'm confused. I thought that the idea of __iadd__ is that for
*mutable* types it modifies existing object instead of returning new
one. So, was that a typo or are Python lists just bad desing:

[1]
 
G

Grant Edwards

As I understand it, this is specific to the implementation of each type.
The only sensible way to code is as if the identity of an object, on
assignment, were completely unpredictable.

The examples you gave showed that integers share identity with other
integers of the same value, while floats do not.

I believe that's only true for small integers, isn't it?
 
P

Peter Hansen

Grant said:
I believe that's only true for small integers, isn't it?

Google finds "LOADI - a fast load instruction for small positive integers
(those referenced by the small_ints array in intobject.c)" and checking
that file is left as an exercise to the reader. I'm going to blindly
assume this is directly related to the issue in question... ;-)

-Peter
 
S

Skip Montanaro

Peter> Google finds "LOADI - a fast load instruction for small positive
Peter> integers (those referenced by the small_ints array in
Peter> intobject.c)"

LOADI was an instruction I implemented a few years ago when investigating
bytecode optimization. It was never added to the Python virtual machine
(ceval.c).

Skip
 
J

Jim Richardson

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

The rule that the object in question is never copied. There are no
exceptions to this. Copying an object requires invoking some method
of the object, or applying some function to the object. For example,
d.copy() returns a (shallow) copy of a dict d, and L[:] returns a
(shallow) copy of a list L.


To clarify for me please.

A shallow copy of an object, returns an object that contains references
to objects within the copied object, yes?

so a list consisting of [1,2,a,"a"] when copied shallowly, will return
exactly that, but when copied deeply, will reture [1,2,"whatever a
points to","a"] yes?

If I understand the above correctly.... how deep does a deep copy go?
can you vary the depth? Or is it binary, shallow or deep?

Thanks.

-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.2 (GNU/Linux)

iD8DBQE/Hr9Bd90bcYOAWPYRAnaYAKDDRFGR6FG3ytgN2dwf7w1shDND3QCgs33B
8jNxKhsF1Ti7bkbPzbCxEx4=
=6a1K
-----END PGP SIGNATURE-----
 
E

Erik Max Francis

Jim said:
A shallow copy of an object, returns an object that contains
references
to objects within the copied object, yes?

so a list consisting of [1,2,a,"a"] when copied shallowly, will return
exactly that, but when copied deeply, will reture [1,2,"whatever a
points to","a"] yes?

No, that's what the first list already consists of:
a = "whatever a points to"
l1 = [1, 2, a, "a"]
l1
[1, 2, 'whatever a points to', 'a']

A shallow copy makes a new object of the object passed in, and maintains
the same reference. A deep copy makes a new object, _and_ a new object
of all references it contains, and on down the line.

The difference between shallow and deep copying is not apparent when
you're talking about immutable objects, since immutable objects need not
ever be literally copied. Consider a simpler case of a list containing
a single element, which is an instance of a custom class:
class C: pass ....
c = C()
x = [c]
y = copy.copy(x)
x is y 0
x[0] is y[0] 1
z = copy.deepcopy(x)
x is z 0
x[0] is z[0] 0
x[0]
<__main__.C instance at 0x814c9fc>

Shallow copying makes a duplicate of the parent object. Deep copying
makes a duplicate of everything.
 
T

Terry Reedy

immutable objects need not ever be literally copied
Shallow copying makes a duplicate of the parent object. Deep copying
makes a duplicate of everything.

To be more exact, because first statement is true,
second_statement.replace('everything', 'all mutables'),
which is to say, 'as much as needed'.
import copy
l1=[(),[]]
l2=copy.deepcopy(l1)
for i in l1+l2: print id(i)
....
7669904
8422784
7669904 #same ()
8428448 #different []

Terry J. Reedy
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,020
Latest member
GenesisGai

Latest Threads

Top