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


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

Fool Python class with imaginary members (serious guru stuff inside)

Started byJure Erznožnik <jure.erznoznik@gmail.com>
First post2012-09-20 06:52 -0700
Last post2012-09-20 19:15 +0000
Articles 3 — 3 participants

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


Contents

  Fool Python class with imaginary members (serious guru stuff inside) Jure Erznožnik <jure.erznoznik@gmail.com> - 2012-09-20 06:52 -0700
    Re: Fool Python class with imaginary members (serious guru stuff inside) Terry Reedy <tjreedy@udel.edu> - 2012-09-20 13:04 -0400
    Re: Fool Python class with imaginary members (serious guru stuff inside) Steven D'Aprano <steve+comp.lang.python@pearwood.info> - 2012-09-20 19:15 +0000

#29552 — Fool Python class with imaginary members (serious guru stuff inside)

FromJure Erznožnik <jure.erznoznik@gmail.com>
Date2012-09-20 06:52 -0700
SubjectFool Python class with imaginary members (serious guru stuff inside)
Message-ID<89b80b56-d1f2-477e-b28a-4410f2cf9de6@googlegroups.com>
I'm trying to create a class that would lie to the user that a member is in some cases a simple variable and in other cases a class. The nature of the member would depend on call syntax like so:
1. x = obj.member #x becomes the "simple" value contained in member
2. x = obj.member.another_member #x becomes the "simple" value contained in first member's another_member.

So the first method "detects" that we only need a simple value and returns that. The second method "sees" that we need "member" as a class and returns that. Note that "simple type" could mean anything, from int to bitmap image.

I have determined that this is possible if I sacrifice the final member reference to the __call__ override using function-call syntax: 1. x = obj.member(). The call syntax returns the simple value and the other returns the class. It is also possible if I override the __xxxitem__ methods to simulate a dictionary.

However, I would like to use the "true member" access syntax if possible.

So, is it possible?

[toc] | [next] | [standalone]


#29561

FromTerry Reedy <tjreedy@udel.edu>
Date2012-09-20 13:04 -0400
Message-ID<mailman.966.1348160696.27098.python-list@python.org>
In reply to#29552
On 9/20/2012 9:52 AM, Jure Erznožnik wrote:
> I'm trying to create a class that would lie to the user that a member is in some cases a simple variable and in other cases a class. The nature of the member would depend on call syntax like so:
> 1. x = obj.member #x becomes the "simple" value contained in member
> 2. x = obj.member.another_member #x becomes the "simple" value contained in first member's another_member.

x.y.z is parsed and executed as (x.y).z, so you are asking if the 
attribute-getter can know what will be done with the object it returns.
Assuming CPython, you would have to write something that searches the 
Python code before compilation, the ast during compilation, or the 
bytecode after compilation.

Much easier would be to define a union class that is a simple type with 
attributes and return that in the first lookup.

class AttrInt(int):
     def __getattr__(self, name): return 'attribute'

y = AttrInt(3)
print(y, y.a)
###
3 attribute

If x.y returns an AttrInt, it will act like an int for most purposes, 
while x.y.z will return whatever AttrInt.__getattr__ does and the 
temporary AttrInt y disappears.

-- 
Terry Jan Reedy

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


#29568

FromSteven D'Aprano <steve+comp.lang.python@pearwood.info>
Date2012-09-20 19:15 +0000
Message-ID<505b6b3a$0$29981$c3e8da3$5496439d@news.astraweb.com>
In reply to#29552
On Thu, 20 Sep 2012 06:52:07 -0700, Jure Erznožnik wrote:

> I'm trying to create a class that would lie to the user that a member is
> in some cases a simple variable and in other cases a class. The nature
> of the member would depend on call syntax like so: 
> 1. x = obj.member #x becomes the "simple" value contained in member 
> 2. x = obj.member.another_member #x becomes the "simple" value
> contained in first member's another_member.

Why do you hate your users so much that you want to cause them enormous 
difficulty with perfectly reasonable code like this?

tmp = obj.member
x = tmp.another_member


> So the first method "detects" that we only need a simple value and
> returns that.

Fortunately that is impossible without nasty bytecode or AST hacks. Thank 
the stars that Python doesn't allow anything as badly designed as this!



-- 
Steven

[toc] | [prev] | [standalone]


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


csiph-web