On 19 May 2015 at 09:50, Chris Angelico <ros...@gmail.com> wrote: > On Tue, May 19, 2015 at 6:39 PM, Marko Rauhamaa <ma...@pacujo.net> wrote: >> For example, you could explain Python's object references as pointers >> (memory addresses) if you considered that helpful. (That's how Lisp >> textbooks often explain cons cells.) > > Sorta-kinda-maybe, but if a C programmer's idea of pointers is invoked > to explain Python's object references, the differences will start to > be problematic: > > 1) Pointer arithmetic simply doesn't exist in Python. Arrays/lists are > not just pointers to their first elements, and subscripting is most > definitely NOT "add to pointer and dereference". > 2) In fact, dereferencing as a whole isn't really a 'thing' either. At > best, it happens automatically. > 3) References actually mean something. Copying a pointer doesn't. > Whether the Python you're using is refcounted (CPython) or > mark-and-sweep (uPy, I think) or some other model, an additional > reference to the same object will prevent it from being disposed of, > which isn't the case in C. > 4) A pointer is itself a value. You can pass a > pointer-to-local-variable to another function and have that function > change a local variable.
I think this is actually one of those areas where the analogy does make sense. In Python if I pass an object as an argument to another function I can mutate the object but I can't rebind the name in the parent frame. Similarly in C I can pass a pointer to anything into another function and the other function will be able to mutate the pointed-to variable but not change the value of the pointer in the parent frame. int b = 2; void f(int* d) { *d = 3; // Changes a which is pointed to by c and d. d = &b; // Doesn't affect c. *d = 4; // Changes b } int main(int argc, char *argv[]) { int a = 1; int *c = &a; // a and *c are the same object f(c); // c still points to a but a is now 3. printf("*c = %d\n", *c); return 0; } The effect is the same in Python except that I can't use an int for the demo since they're immutable: b = [2] def g(d): d[0] = 3 # Changes a which is also c and d d = b # Doesn't affect a or c d[0] = 4 # Changes b def main(): a = [1] c = a # a and c are the same object f(c) # c is still a but a is now [3] print("c =", c) main() Having taught beginners to program with C as a first programming language and with Python as a first programming language I would say that in either case this is an important fundamental concept that beginners need to get their heads round. If a C programmer finds it easier to understand how Python handles it by relating it to pointers then that's great. > 5) Furthermore, since a pointer is a value, you can have pointers to > pointers, etc. Doesn't make any sense in Python. You can have a reference to a container object which references other objects. The effect is more or less the same if you want to understand how something like this works: a = [[0] * 5] * 5 -- Oscar -- https://mail.python.org/mailman/listinfo/python-list