Groups | Search | Server Info | Keyboard shortcuts | Login | Register [http] [https] [nntp] [nntps]


Groups > comp.lang.python > #86214 > unrolled thread

list storing variables

Started by"ast" <nomail@invalid.com>
First post2015-02-23 13:55 +0100
Last post2015-02-24 10:18 +0200
Articles 14 — 9 participants

Back to article view | Back to comp.lang.python


Contents

  list storing variables "ast" <nomail@invalid.com> - 2015-02-23 13:55 +0100
    Re: list storing variables Dave Angel <davea@davea.name> - 2015-02-23 08:24 -0500
    Re: list storing variables Marko Rauhamaa <marko@pacujo.net> - 2015-02-23 15:49 +0200
    Re: list storing variables Peter Pearson <pkpearson@nowhere.invalid> - 2015-02-23 17:35 +0000
      Re: list storing variables Marko Rauhamaa <marko@pacujo.net> - 2015-02-23 20:22 +0200
        Re: list storing variables Peter Otten <__peter__@web.de> - 2015-02-23 19:41 +0100
          Re: list storing variables Marko Rauhamaa <marko@pacujo.net> - 2015-02-23 21:06 +0200
            Re: list storing variables Chris Angelico <rosuav@gmail.com> - 2015-02-24 06:17 +1100
              Re: list storing variables Marko Rauhamaa <marko@pacujo.net> - 2015-02-23 22:25 +0200
            Re: list storing variables Ian Kelly <ian.g.kelly@gmail.com> - 2015-02-23 12:29 -0700
              Re: list storing variables Marko Rauhamaa <marko@pacujo.net> - 2015-02-23 22:38 +0200
    Re: list storing variables Ben Finney <ben+python@benfinney.id.au> - 2015-02-24 09:03 +1100
      Re: list storing variables Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2015-02-24 13:24 +1100
        Re: list storing variables Marko Rauhamaa <marko@pacujo.net> - 2015-02-24 10:18 +0200

#86214 — list storing variables

From"ast" <nomail@invalid.com>
Date2015-02-23 13:55 +0100
Subjectlist storing variables
Message-ID<54eb2357$0$3011$426a74cc@news.free.fr>
hi

>>> a = 2; b = 5
>>> Li = [a, b]
>>> 
>>> Li
[2, 5]
>>> a=3
>>> Li
[2, 5]
>>> 

Ok, a change in a or b doesn't impact Li. This works as expected

Is there a way to define a container object able to store some variables 
so that a change of a variable make a change in this object content ?

I dont need this feature. It is just something I am thinking about.

In C language, there is &A for address of A

[toc] | [next] | [standalone]


#86215

FromDave Angel <davea@davea.name>
Date2015-02-23 08:24 -0500
Message-ID<mailman.19069.1424697860.18130.python-list@python.org>
In reply to#86214
On 02/23/2015 07:55 AM, ast wrote:
> hi
>
>>>> a = 2; b = 5
>>>> Li = [a, b]
>>>>
>>>> Li
> [2, 5]
>>>> a=3
>>>> Li
> [2, 5]
>>>>
>
> Ok, a change in a or b doesn't impact Li. This works as expected
>
> Is there a way to define a container object able to store some variables
> so that a change of a variable make a change in this object content ?
>
> I dont need this feature. It is just something I am thinking about.
>
> In C language, there is &A for address of A
>

When you do an "a=3"  you are rebinding a, and that has no connection to 
what's in the list.  If you were to modify the object that a and L1[0] 
share, then yes, the modifications would affect both sides.

However, an int is immutable, so you cannot directly do it.

The simplest approximation to what you're asking is to use a list within 
the list.

a = [42]; b = 65
L1 = [a, b]
a[0] = 99       #this doesn't rebind a, just changes the list
                 # object it is bound to
print(L1)

yields:
[[99], 65]

Clearly, instead of a list, you could use some other mutable object.  In 
fact, you could use something like:

class Dummy(object):
     pass

a = Dummy()
a.value = 12
...


-- 
DaveA

[toc] | [prev] | [next] | [standalone]


#86220

FromMarko Rauhamaa <marko@pacujo.net>
Date2015-02-23 15:49 +0200
Message-ID<87fv9wd9gw.fsf@elektro.pacujo.net>
In reply to#86214
"ast" <nomail@invalid.com>:

> Is there a way to define a container object able to store some
> variables so that a change of a variable make a change in this object
> content ?
>
> I dont need this feature. It is just something I am thinking about.
>
> In C language, there is &A for address of A

In Python, you can accomplish "&" by creating an object:

   >>> a = 3
   >>> b = 4
   >>> class AmpersandA:
   ...     def get(self): return a
   ...     def set(self, value): global a; a = value
   ... 
   >>> class AmpersandB:
   ...     def get(self): return b
   ...     def set(self, value): global b; b = value
   ... 
   >>> l = [ AmpersandA(), AmpersandB() ]
   >>> for m in l:
   ...     m.set(7)
   ... 
   >>> print(a)
   7
   >>> print(b)
   7
   >>> 

It's exactly like "&" in C escept it's a slight bit more verbose and the
exact implementation is dependent on the name of the variable.


Marko

[toc] | [prev] | [next] | [standalone]


#86247

FromPeter Pearson <pkpearson@nowhere.invalid>
Date2015-02-23 17:35 +0000
Message-ID<cl16ncF4a8mU1@mid.individual.net>
In reply to#86214
On Mon, 23 Feb 2015 13:55:47 +0100, ast <nomail@invalid.com> wrote:
> hi
>
>>>> a = 2; b = 5
>>>> Li = [a, b]
>>>> 
>>>> Li
> [2, 5]
>>>> a=3
>>>> Li
> [2, 5]
>>>> 
>
> Ok, a change in a or b doesn't impact Li. This works as expected
>
> Is there a way to define a container object able to store some variables 
> so that a change of a variable make a change in this object content ?
>
> I dont need this feature. It is just something I am thinking about.
>
> In C language, there is &A for address of A

The word "variable" brings implications and assumptions that get
people into trouble in Python.  Python doesn't have variables.
It has objects, and you can assign names to objects -- like sticky
notes, as someone in this newsgroup helpfully pointed out long ago.

This way of thinking is significantly different from the familiar
"variable" mind-set of C, but looks similar enough to produce some 
confusion.  For me, the sticky-note analogy helped a lot, and in a
few days many things made more sense.

-- 
To email me, substitute nowhere->runbox, invalid->com.

[toc] | [prev] | [next] | [standalone]


#86251

FromMarko Rauhamaa <marko@pacujo.net>
Date2015-02-23 20:22 +0200
Message-ID<8761ascwt4.fsf@elektro.pacujo.net>
In reply to#86247
Peter Pearson <pkpearson@nowhere.invalid>:

>>>>> a = 2; b = 5
>>>>> Li = [a, b]
>>>>> Li
>> [2, 5]
>>>>> a=3
>>>>> Li
>> [2, 5]
>
> [...]
>
> The word "variable" brings implications and assumptions that get
> people into trouble in Python.  Python doesn't have variables.
> It has objects, and you can assign names to objects -- like sticky
> notes, as someone in this newsgroup helpfully pointed out long ago.
>
> This way of thinking is significantly different from the familiar
> "variable" mind-set of C, but looks similar enough to produce some 
> confusion.  For me, the sticky-note analogy helped a lot, and in a
> few days many things made more sense.

It's no different in C:

   #include <stdio.h>

   int main()
   {
      int a = 2, b = 5;
      int Li[2] = { a, b };
      printf("%d %d\n", Li[0], Li[1]);
      a = 3;
      printf("%d %d\n", Li[0], Li[1]);
      return 0;
   }

Outputs:

   2 5
   2 5


Marko

[toc] | [prev] | [next] | [standalone]


#86253

FromPeter Otten <__peter__@web.de>
Date2015-02-23 19:41 +0100
Message-ID<mailman.19094.1424716896.18130.python-list@python.org>
In reply to#86251
Marko Rauhamaa wrote:

> Peter Pearson <pkpearson@nowhere.invalid>:
> 
>>>>>> a = 2; b = 5
>>>>>> Li = [a, b]
>>>>>> Li
>>> [2, 5]
>>>>>> a=3
>>>>>> Li
>>> [2, 5]
>>
>> [...]
>>
>> The word "variable" brings implications and assumptions that get
>> people into trouble in Python.  Python doesn't have variables.
>> It has objects, and you can assign names to objects -- like sticky
>> notes, as someone in this newsgroup helpfully pointed out long ago.
>>
>> This way of thinking is significantly different from the familiar
>> "variable" mind-set of C, but looks similar enough to produce some
>> confusion.  For me, the sticky-note analogy helped a lot, and in a
>> few days many things made more sense.
> 
> It's no different in C:
> 
>    #include <stdio.h>
> 
>    int main()
>    {
>       int a = 2, b = 5;
>       int Li[2] = { a, b };
>       printf("%d %d\n", Li[0], Li[1]);
>       a = 3;
>       printf("%d %d\n", Li[0], Li[1]);
>       return 0;
>    }
> 
> Outputs:
> 
>    2 5
>    2 5
> 
> 
> Marko

The OP explicitly mentions the & operator. There's no python analog to that 
and the behavior shown below:

$ cat pointers.c
#include <stdio.h>

int main()
{
  int a = 2, b = 5;
  int * Li[2] = { &a, &b };
  printf("%d %d\n", *Li[0], *Li[1]);
  a = 3;
  printf("%d %d\n", *Li[0], *Li[1]);
  return 0;
}
$ gcc pointers.c
$ ./a.out 
2 5
3 5

[toc] | [prev] | [next] | [standalone]


#86255

FromMarko Rauhamaa <marko@pacujo.net>
Date2015-02-23 21:06 +0200
Message-ID<87385wh2ho.fsf@elektro.pacujo.net>
In reply to#86253
Peter Otten <__peter__@web.de>:

> The OP explicitly mentions the & operator. There's no python analog to
> that and the behavior shown below:
>
> $ cat pointers.c
> #include <stdio.h>
>
> int main()
> {
>   int a = 2, b = 5;
>   int * Li[2] = { &a, &b };
>   printf("%d %d\n", *Li[0], *Li[1]);
>   a = 3;
>   printf("%d %d\n", *Li[0], *Li[1]);
>   return 0;
> }
> $ gcc pointers.c
> $ ./a.out 
> 2 5
> 3 5

But there is! I just demonstrated it in a previous posting:

> In Python, you can accomplish "&" by creating an object:
> 
>    >>> a = 3
>    >>> b = 4
>    >>> class AmpersandA:
>    ...     def get(self): return a
>    ...     def set(self, value): global a; a = value
>    ... 
>    >>> class AmpersandB:
>    ...     def get(self): return b
>    ...     def set(self, value): global b; b = value
>    ... 
>    >>> l = [ AmpersandA(), AmpersandB() ]
>    >>> for m in l:
>    ...     m.set(7)
>    ... 
>    >>> print(a)
>    7
>    >>> print(b)
>    7
>    >>> 
> 
> It's exactly like "&" in C escept it's a slight bit more verbose and the
> exact implementation is dependent on the name of the variable.

You can find an analogous ampersand object for any C lvalue.

What I'm saying is that there's nothing special about Python's object
model or variables. Guido could decide tomorrow to add a C-esque "&"
operator to Python without breaking a single existing Python program.
The Python compiler would simply generate code like above.


Marko

[toc] | [prev] | [next] | [standalone]


#86256

FromChris Angelico <rosuav@gmail.com>
Date2015-02-24 06:17 +1100
Message-ID<mailman.19096.1424719540.18130.python-list@python.org>
In reply to#86255
On Tue, Feb 24, 2015 at 6:06 AM, Marko Rauhamaa <marko@pacujo.net> wrote:
> What I'm saying is that there's nothing special about Python's object
> model or variables. Guido could decide tomorrow to add a C-esque "&"
> operator to Python without breaking a single existing Python program.
> The Python compiler would simply generate code like above.

Actually, there's a fairly huge difference. All you've done is create
a thing which can set a global... you don't have any way to pass
pointers around, like you can in C. (And that's even without getting
into pointer *arithmetic*.) You have to construct a dedicated "thing"
in your source code for every pointer you want to be able to work
with. And if you try to make a single generic "Ampersand" class, what
you'll find is that you're working with namespaces, not addresses. So
Python's name-binding model really is fundamentally different from C's
stuff-in-memory model.

ChrisA

[toc] | [prev] | [next] | [standalone]


#86261

FromMarko Rauhamaa <marko@pacujo.net>
Date2015-02-23 22:25 +0200
Message-ID<87oaokfk9p.fsf@elektro.pacujo.net>
In reply to#86256
Chris Angelico <rosuav@gmail.com>:

> On Tue, Feb 24, 2015 at 6:06 AM, Marko Rauhamaa <marko@pacujo.net> wrote:
>> What I'm saying is that there's nothing special about Python's object
>> model or variables. Guido could decide tomorrow to add a C-esque "&"
>> operator to Python without breaking a single existing Python program.
>> The Python compiler would simply generate code like above.
>
> Actually, there's a fairly huge difference. All you've done is create
> a thing which can set a global... you don't have any way to pass
> pointers around, like you can in C.

That AmpersandA() object *is* a first-class "pointer" object. It can be
passed around freely just like &A in C.

> You have to construct a dedicated "thing" in your source code for
> every pointer you want to be able to work with.

Yes. Python doesn't have language-level support for the construct, but
it could be added without a change in the data model.

> And if you try to make a single generic "Ampersand" class, what
> you'll find is that you're working with namespaces, not addresses.

I wasn't trying to make a single generic Ampersand class.

> So Python's name-binding model really is fundamentally different from
> C's stuff-in-memory model.

I still fail to see the fundamental difference.

The main difference between the "old" languages and the "new" languages
is the lack of "boxing" in the "new" languages. In C terms, Python's "."
is C's "->".


Marko

[toc] | [prev] | [next] | [standalone]


#86257

FromIan Kelly <ian.g.kelly@gmail.com>
Date2015-02-23 12:29 -0700
Message-ID<mailman.19097.1424719816.18130.python-list@python.org>
In reply to#86255
On Mon, Feb 23, 2015 at 12:06 PM, Marko Rauhamaa <marko@pacujo.net> wrote:
> But there is! I just demonstrated it in a previous posting:
>
>> In Python, you can accomplish "&" by creating an object:
>>
>>    >>> a = 3
>>    >>> b = 4
>>    >>> class AmpersandA:
>>    ...     def get(self): return a
>>    ...     def set(self, value): global a; a = value
>>    ...
>>    >>> class AmpersandB:
>>    ...     def get(self): return b
>>    ...     def set(self, value): global b; b = value
>>    ...
>>    >>> l = [ AmpersandA(), AmpersandB() ]
>>    >>> for m in l:
>>    ...     m.set(7)
>>    ...
>>    >>> print(a)
>>    7
>>    >>> print(b)
>>    7
>>    >>>
>>
>> It's exactly like "&" in C escept it's a slight bit more verbose and the
>> exact implementation is dependent on the name of the variable.

"Sure, you can have list comprehensions in C! Just write a function
whose arguments are two other functions and an input array."

Obviously one can use any Turing-complete language to emulate features
of any other Turing-complete language, but I think the point is that
there is no syntactic support for it.

[toc] | [prev] | [next] | [standalone]


#86262

FromMarko Rauhamaa <marko@pacujo.net>
Date2015-02-23 22:38 +0200
Message-ID<87k2z8fjn3.fsf@elektro.pacujo.net>
In reply to#86257
Ian Kelly <ian.g.kelly@gmail.com>:

> Obviously one can use any Turing-complete language to emulate features
> of any other Turing-complete language, but I think the point is that
> there is no syntactic support for it.

While my "contribution" was made tongue-in-cheek, there's a grain of
truth in every joke.

First of all, this is not emulating a Turing-complete language. It is
demonstrating differences in the data model. The differences aren't in
the supposed absence of variables or memory slots. Python has variables
that are memory slots, just like C or Java.

You are right that Python doesn't have syntactic support for "&".
However, that has little bearing to the underlying data model.

Python doesn't suffer from the absence of "&" as much as Java does, for
example, because its main use case is returning multiple values. Tuples
handle that just fine -- although, look at this snippet:

    def put_left(self, key, value):
        if self.left is None:
            self.left = Entry(self, key, value)
            self.balance -= 1
            return self, self.right is None, self.left, True
        self.left, grown, entry, fresh = self.left.put(key, value)
        if not grown:
            return self, False, entry, fresh
        self.balance -= 1
        if self.balance != -2:
            return self, self.balance == -1, entry, fresh
        return self.rotate_right(), False, entry, fresh


There are other, rarer use cases where idioms such as my AmpersandA
class need to be employed. But, thanks to the existence of closures, no
tears are shed.


Marko

[toc] | [prev] | [next] | [standalone]


#86271

FromBen Finney <ben+python@benfinney.id.au>
Date2015-02-24 09:03 +1100
Message-ID<mailman.19104.1424728988.18130.python-list@python.org>
In reply to#86214
"ast" <nomail@invalid.com> writes:

> Ok, a change in a or b doesn't impact Li. This works as expected

Because a container stores references to objects. The other references
(such as names) that object might have are not stored.

> Is there a way to define a container object able to store some
> variables so that a change of a variable make a change in this object
> content ?

As has been pointed out, Python does not have “variables” in the sense
of a named box containing a value.

What Python does have is a mapping type. You can store a key → value
mapping for each value you want to reference later.

    >>> a = 2; b = 5
    >>> foo = {'a': a, 'b': b}
    >>> foo
    {'b': 5, 'a': 2}
    >>> foo['a'] = 3
    >>> foo
    {'b': 5, 'a': 3}

You appear, though, to want this to somehow automatically track the
changes in name bindings. No, there's no way to do that except
explicitly coding it yourself.

> In C language, there is &A for address of A

There is no “address of a value” concept in Python. You access a value
by some reference, either a name or an item in a collection. When a
reference changes to reference some different value, other references
are not affected.

-- 
 \        “All opinions are not equal. Some are a very great deal more |
  `\   robust, sophisticated, and well supported in logic and argument |
_o__)                                     than others.” —Douglas Adams |
Ben Finney

[toc] | [prev] | [next] | [standalone]


#86288

FromSteven D'Aprano <steve+comp.lang.python@pearwood.info>
Date2015-02-24 13:24 +1100
Message-ID<54ebe0c8$0$11114$c3e8da3@news.astraweb.com>
In reply to#86271
Ben Finney wrote:

>> In C language, there is &A for address of A
> 
> There is no “address of a value” concept in Python. You access a value
> by some reference, either a name or an item in a collection. When a
> reference changes to reference some different value, other references
> are not affected.

Furthermore, in Python, values can *change their address*.

Jython and IronPython both are built on top of a garbage collector which can 
move memory around, meaning that objects can end up in a completely 
different location. This makes no difference to Python code, and there is no 
supported way of getting to the address of an object. (In fact, objects may 
be split over multiple locations, even in CPython, e.g. the new optimized 
implementation for dicts has shared storage for keys.)


-- 
Steve

[toc] | [prev] | [next] | [standalone]


#86306

FromMarko Rauhamaa <marko@pacujo.net>
Date2015-02-24 10:18 +0200
Message-ID<87385ven8x.fsf@elektro.pacujo.net>
In reply to#86288
Steven D'Aprano <steve+comp.lang.python@pearwood.info>:

> Ben Finney wrote:
>> There is no “address of a value” concept in Python.
>
> Furthermore, in Python, values can *change their address*.
>
> Jython and IronPython both are built on top of a garbage collector
> which can move memory around, meaning that objects can end up in a
> completely different location. This makes no difference to Python
> code, and there is no supported way of getting to the address of an
> object. (In fact, objects may be split over multiple locations, even
> in CPython, e.g. the new optimized implementation for dicts has shared
> storage for keys.)

You are taking the concept of "address" far too literally, and yet not
literally enough.

Even in C programs, the *physical* address of a variable/value can
change at any point without warning.

In abstract terms, an address is a reference. And that reference stays
still in both C and Python. What happens under the hood of the data
model is irrelevant.


Marko

[toc] | [prev] | [standalone]


Back to top | Article view | comp.lang.python


csiph-web