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

2012-09-20 Thread Jure Erznožnik
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?
-- 
http://mail.python.org/mailman/listinfo/python-list


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

2012-09-20 Thread Terry Reedy

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


--
http://mail.python.org/mailman/listinfo/python-list


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

2012-09-20 Thread Steven D'Aprano
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
-- 
http://mail.python.org/mailman/listinfo/python-list