
first thing: properties. i prefer this approach to properties (example below). true, it involves some magic, but the magic is very restricted and contained. import inspect def getter(func): namespace = inspect.stack()[1][0].f_locals p = namespace.get(func.func_name) if p is None: p = property(func) else: p = property(func, p.fset, p.fdel) return p def setter(func): namespace = inspect.stack()[1][0].f_locals p = namespace.get(func.func_name) if p is None: p = property(None, func) else: p = property(p.fget, func, p.fdel) return p class File(object): def __init__(self): self._pos = 8 @getter def position(self): return self._pos @setter def position(self, value): self._pos = value f = File() print f.position f.position = 11 print f.position ============================================== btw, in py3k, with class decorators, you could instead use class File: @propertyclass class position: def get(self): return self.tell() def set(self): return self.tell() ============================================== second -- metaclasses. there's some notion (Josiah et al) that metaclasses were introduced to make classes behave as generic attribute containers. this is not true. using metaclasses like so was not the original intent. metaclasses are the types of types. they also happened to be executed before the class body is made into a class, which means they can be used to tweak class creation, but that's a technicality. using this feature to turn classes into anything you want is wrong: it's implicit, complex, and mostly unreadable by the common programmer. i'd guess 80% of python programmers have never used metaclasses. it's a difficult concept, and should be used sparsely. class decorators would cover ~70% of the use-cases for metaclasses, but for some reason, people insist on complicating even more the metaclass machinery in py3k. see my protest [1], which was silently ignored. what you people are asking for is a new language construct which allows the definition of syntactic namespaces. much like the deceased make pep. (mis)using classes for this purpose is wrong. it's different -- it's not a class anymore. so why is it being defined by a class-clause? @property namespace foo: def get(self): .... def set(self): .... -tomer [1] http://mail.python.org/pipermail/python-3000/2007-June/008330.html

tomer filiba wrote:
first thing: properties. i prefer this approach to properties (example below). true, it involves some magic, but the magic is very restricted and contained.
Looks good, it also looks optional in that the old way still works. Here are my recent thoughts on properties, which I believe would create more problems than not, but maybe someone can think of a nicer way to do the same thing? (shrug) (This isn't thought out fully.) Properties are magic anyways. Yes, they can be implemented in pythons existing machinery, but that doesn't make them any less magical in what they do. For example, *what if* properties could be defined independently of class's? (possible?) They would act something like a true variable or a unique mutable container of length one. This is unique in python because in all other cases the expression (x = y) would be a name binding operation. With a property, it's a closer to (x[0] = y). Because it's behavior is unique, it would probably need it's own constructor syntax, as well as support by the interpreter to recognize them and call the setter and getter functions instead of rebinding the name. It would need to convert (x = y) statements where x is a property to (x.__set__(y)). So a global property definition might look something like... property foo(): __value__ = value def __get__(): return __value__ def __set__(value) __value__ = value Of course that would be magic since it isn't a class and it isn't a function. It's a mutable variable with definable input and output functions. And it has a problem in that there is no way to create a lot of them without resorting to meta programming techniques. So we are back to first creating a function or a class, and then converting it to a property in some *magical* way. The same object in a class might look like... property foo(self): self.__value__ = None def __get__(self): return self.__value__ def __set__(self, value): self.__value__ = value This is sort of the direction some of the other suggestions have been going in I think. But how useful would it be? In other words, would something like property objects be useful and beneficial behavior to the language? My personal thoughts at this time are it would probably be more trouble than it's worth even thought there are certain aspects to the general idea I like. There is more things about how to make it work I don't like.
I haven't needed them yet, but I do wonder how I might use them to generalize certain types of behaviors across a wider range of objects and situations. So far though I've found it easier to just stay away from them.
I think I agree that there seems to be a indirect need if not desire to have an explicit name space type of object. It seems like it may have the potential to improve some types of name space operations where dictionaries are currently used.
I think that should be... def set(self, value): ... Then it's not too different from what I described above. ;-) There may also be no requirement for a property type to have a single value. So a property with child values could also be a name space or the other way around. A name space with only it's primary value could be a property. Cheers, Ron

Ron Adam wrote:
In the first version, how is anything supposed to know that the __value__ inside the function is an implicit attribute of self rather than a local variable of the function I can't see this flying, for all the reasons that suggestions for implicit 'self' in methods get shot down in milliseconds. -- Greg

Greg Ewing wrote:
This should have been __value__ = None.
In the first example self isn't implicit, it's non-existent. It would work more like a generator that yields it value on gets, and receives its value on sets. In the second version self is passed to the functions explicitly so it can work in an instance. But other than that it's the same. It could also keep state between calls, in which case all instances of that class would share those values. (just like instances share class attributes) class bar(object): property foo(self): countgets = 0 self.__value__ = None def __get__() countgets += 1 return countgets, self.__value__ def __set__(value) self.__value__ = value In this case countgets will be the total gets of all subclasses of bar. This could be done with a class attribute as well, but that breaks the idea of having a single self contained component. Having self contained components is more conducive to a modular design where you can more easily reuse parts. Cheers, Ron
I can't see this flying, for all the reasons that suggestions for implicit 'self' in methods get shot down in milliseconds.
I can see that. I actually like self. :-) The feature I recently wanted was a dynamic __contained_in__ attribute to go along with self. But on a wider scale than class's self. For example an object in a list could get a reference to the list object it's in. (or dictionary, function, class, etc.) And if you moved that object to another container, the __contained_in__, attribute would change to reflect that. The reason I wanted that is it can get around the chicken and egg situation of having to construct windows and frames in tkinter before creating the objects that go in them. I wanted to create the buttons and lables and other interior items first and then add them to frames later by appending them to a list like frame object. It could completely do away with the need to pass handles around. But there are places were you really need to construct things in a certain order. Cheers, Ron

On 7/24/07, Ron Adam <rrr@ronadam.com> wrote:
Pardon me for interrupting... Don't the existing descriptors do all of this, with almost exactly the same syntax? You just have to set a class variable to an instance of the descriptor class, which is one extra line of code. Additionally, this allows reuse of a descriptor class for multiple properties, which as-far-as-I-can-tell your models don't. Perhaps I'm missing something, but I can't see the actual benefit of your suggestions (besides inline-ing of properties' names). - Tal

Tal Einat wrote:
You aren't interrupting at all, but adding to it. ;-)
Yes you are correct and it is why I said at the beginning one of the problems is you can't make a lot of these without resorting to meta programming techniques.
Perhaps I'm missing something, but I can't see the actual benefit of your suggestions (besides inline-ing of properties' names).
Inline-ing property names isn't really the point at all. A much bigger change is having a way to use them outside of classes for indirect references. foo = ['a', 'b', 'c', 'd'] property thirdfoo(): def __get__(): return foo[3] def __set__(value): foo[n] = value print thirdfoo ---> 'c' thirdfoo = 'z' # Doesn't rebind thirdfoo to 'z'! print thirdfoo ---> 'z' print foo ---> ['a', 'b', 'z', 'd'] Now as far as re-use goes, it could be more like a class with an __init__ method. Then it becomes almost exactly like the current descriptor objects too. (Maybe a good thing.) The reason 'class' is replaced by 'property' is that it needs some way to tell the interpreter that this has different access characteristics than a normal name/object binding so it can be used outside of a class. That change (potentially) makes descriptors/properties independent from the classes they are in. Another way to do it might be to have a indirect name space. Then it becomes a matter of moving a class (or suitable function) to "indirect" to activate it as a local descriptor. Or "__indirect__" in the case of class descriptors. And yes this is still a rather abstract idea. The question is would it be beneficial to generalize and formalize descriptors and properties? (but not necessarily in the exact manner I'm describing.) Cheers, Ron

Ron Adam <rrr@ronadam.com> wrote:
I would argue no. Non-dotted assignments resulting in arbitrary code execution sounds to me like a metric ton of magic and a great way of confusing the hell out of any and all future readers of your code. I know I'm a curmudgeon when it comes to syntax, but I would really like to see a *sane* use-case for the potential feature (though I doubt one exists). - Josiah

Josiah Carlson wrote:
I would really like to see a *sane* use-case for the potential feature
I would like to have some reasonable way of achieving the effect of a __getattr__ for a module, so that I could implement auto-loaded classes. You can do this now, but the convolutions required are horrible to behold. I don't think this particular proposal is the way to go about it, though. -- Greg

Greg Ewing <greg.ewing@canterbury.ac.nz> wrote:
It's already possible. >>> import sys >>> class foo(object): ... def __getattr__(self, clsname): ... return type(clsname, (object,), {}) ... >>> sys.modules['loader'] = foo() >>> from loader import bar >>> bar <class '__main__.bar'> >>> import loader >>> loader.boo <class '__main__.boo'> >>> - Josiah

Josiah Carlson wrote:
Yes, that's the sort of ugly hack I was talking about (although mine was slightly worse, involving a module replacing itself with a subclass of module and then re-importing itself). I keep thinking there ought to be a neater way, although I haven't figured out exactly what it should look like. -- Greg

"tomer filiba" <tomerfiliba@gmail.com> wrote:
first thing: properties. i prefer this approach to properties (example below). true, it involves some magic, but the magic is very restricted and contained.
[snip] I'm not a big fan of the style that you propose. It doesn't fit my aesthetics. I'd rather introduce another level of indentation with a class statement than to confuse myself with generic-like decoration that aren't actually generics.
I have never made any claim that they were introduced to offer that functionality (incidentally, I don't believe anyone else has claimed as much on this list either), I stated that they *could be used* to offer that functionality, expressed that I had done so, and in my opinion, using them as a generic container was obvious. If others disagree with my opinions, that's fine, but please don't put words into my mouth.
If metaclasses are rarely used by users, then where is the problem of using (and abusing) them if a person desires?
Don't get me wrong, I've been pushing for class decorators for a couple years now (after 2.4 was released without them), and also generally dislike the uglification of metaclass semantics, but every extra argument to 'class foo(<arguments>):' necessarily makes it an uglier mess than it already is. Yes, overloading metaclasses to return a dictionary-like object as a namespace is ugly, but getting the 'order' list in '(name, bases, attrs, order)' to be correct when confronted with 'del' is tricky, and will necessarily require an extra line of boilerplate. Of course whether this is a bigger issue than everyone writing their own ordered dict, is another dicussion (that I don't particularly want to participate in).
Because it offers everything necessary for certain higher order functionality without needing to change the base language. I don't know about others, but I am conservative about language change. I believe that Python should be no simpler and no more complex than necessary. Adding yet another way of defining a namespace (with a namespace construct as you propose) won't offer us anything that we don't already have with 'class namespace'. - Josiah

tomer filiba wrote:
first thing: properties. i prefer this approach to properties (example below). true, it involves some magic, but the magic is very restricted and contained.
Looks good, it also looks optional in that the old way still works. Here are my recent thoughts on properties, which I believe would create more problems than not, but maybe someone can think of a nicer way to do the same thing? (shrug) (This isn't thought out fully.) Properties are magic anyways. Yes, they can be implemented in pythons existing machinery, but that doesn't make them any less magical in what they do. For example, *what if* properties could be defined independently of class's? (possible?) They would act something like a true variable or a unique mutable container of length one. This is unique in python because in all other cases the expression (x = y) would be a name binding operation. With a property, it's a closer to (x[0] = y). Because it's behavior is unique, it would probably need it's own constructor syntax, as well as support by the interpreter to recognize them and call the setter and getter functions instead of rebinding the name. It would need to convert (x = y) statements where x is a property to (x.__set__(y)). So a global property definition might look something like... property foo(): __value__ = value def __get__(): return __value__ def __set__(value) __value__ = value Of course that would be magic since it isn't a class and it isn't a function. It's a mutable variable with definable input and output functions. And it has a problem in that there is no way to create a lot of them without resorting to meta programming techniques. So we are back to first creating a function or a class, and then converting it to a property in some *magical* way. The same object in a class might look like... property foo(self): self.__value__ = None def __get__(self): return self.__value__ def __set__(self, value): self.__value__ = value This is sort of the direction some of the other suggestions have been going in I think. But how useful would it be? In other words, would something like property objects be useful and beneficial behavior to the language? My personal thoughts at this time are it would probably be more trouble than it's worth even thought there are certain aspects to the general idea I like. There is more things about how to make it work I don't like.
I haven't needed them yet, but I do wonder how I might use them to generalize certain types of behaviors across a wider range of objects and situations. So far though I've found it easier to just stay away from them.
I think I agree that there seems to be a indirect need if not desire to have an explicit name space type of object. It seems like it may have the potential to improve some types of name space operations where dictionaries are currently used.
I think that should be... def set(self, value): ... Then it's not too different from what I described above. ;-) There may also be no requirement for a property type to have a single value. So a property with child values could also be a name space or the other way around. A name space with only it's primary value could be a property. Cheers, Ron

Ron Adam wrote:
In the first version, how is anything supposed to know that the __value__ inside the function is an implicit attribute of self rather than a local variable of the function I can't see this flying, for all the reasons that suggestions for implicit 'self' in methods get shot down in milliseconds. -- Greg

Greg Ewing wrote:
This should have been __value__ = None.
In the first example self isn't implicit, it's non-existent. It would work more like a generator that yields it value on gets, and receives its value on sets. In the second version self is passed to the functions explicitly so it can work in an instance. But other than that it's the same. It could also keep state between calls, in which case all instances of that class would share those values. (just like instances share class attributes) class bar(object): property foo(self): countgets = 0 self.__value__ = None def __get__() countgets += 1 return countgets, self.__value__ def __set__(value) self.__value__ = value In this case countgets will be the total gets of all subclasses of bar. This could be done with a class attribute as well, but that breaks the idea of having a single self contained component. Having self contained components is more conducive to a modular design where you can more easily reuse parts. Cheers, Ron
I can't see this flying, for all the reasons that suggestions for implicit 'self' in methods get shot down in milliseconds.
I can see that. I actually like self. :-) The feature I recently wanted was a dynamic __contained_in__ attribute to go along with self. But on a wider scale than class's self. For example an object in a list could get a reference to the list object it's in. (or dictionary, function, class, etc.) And if you moved that object to another container, the __contained_in__, attribute would change to reflect that. The reason I wanted that is it can get around the chicken and egg situation of having to construct windows and frames in tkinter before creating the objects that go in them. I wanted to create the buttons and lables and other interior items first and then add them to frames later by appending them to a list like frame object. It could completely do away with the need to pass handles around. But there are places were you really need to construct things in a certain order. Cheers, Ron

On 7/24/07, Ron Adam <rrr@ronadam.com> wrote:
Pardon me for interrupting... Don't the existing descriptors do all of this, with almost exactly the same syntax? You just have to set a class variable to an instance of the descriptor class, which is one extra line of code. Additionally, this allows reuse of a descriptor class for multiple properties, which as-far-as-I-can-tell your models don't. Perhaps I'm missing something, but I can't see the actual benefit of your suggestions (besides inline-ing of properties' names). - Tal

Tal Einat wrote:
You aren't interrupting at all, but adding to it. ;-)
Yes you are correct and it is why I said at the beginning one of the problems is you can't make a lot of these without resorting to meta programming techniques.
Perhaps I'm missing something, but I can't see the actual benefit of your suggestions (besides inline-ing of properties' names).
Inline-ing property names isn't really the point at all. A much bigger change is having a way to use them outside of classes for indirect references. foo = ['a', 'b', 'c', 'd'] property thirdfoo(): def __get__(): return foo[3] def __set__(value): foo[n] = value print thirdfoo ---> 'c' thirdfoo = 'z' # Doesn't rebind thirdfoo to 'z'! print thirdfoo ---> 'z' print foo ---> ['a', 'b', 'z', 'd'] Now as far as re-use goes, it could be more like a class with an __init__ method. Then it becomes almost exactly like the current descriptor objects too. (Maybe a good thing.) The reason 'class' is replaced by 'property' is that it needs some way to tell the interpreter that this has different access characteristics than a normal name/object binding so it can be used outside of a class. That change (potentially) makes descriptors/properties independent from the classes they are in. Another way to do it might be to have a indirect name space. Then it becomes a matter of moving a class (or suitable function) to "indirect" to activate it as a local descriptor. Or "__indirect__" in the case of class descriptors. And yes this is still a rather abstract idea. The question is would it be beneficial to generalize and formalize descriptors and properties? (but not necessarily in the exact manner I'm describing.) Cheers, Ron

Ron Adam <rrr@ronadam.com> wrote:
I would argue no. Non-dotted assignments resulting in arbitrary code execution sounds to me like a metric ton of magic and a great way of confusing the hell out of any and all future readers of your code. I know I'm a curmudgeon when it comes to syntax, but I would really like to see a *sane* use-case for the potential feature (though I doubt one exists). - Josiah

Josiah Carlson wrote:
I would really like to see a *sane* use-case for the potential feature
I would like to have some reasonable way of achieving the effect of a __getattr__ for a module, so that I could implement auto-loaded classes. You can do this now, but the convolutions required are horrible to behold. I don't think this particular proposal is the way to go about it, though. -- Greg

Greg Ewing <greg.ewing@canterbury.ac.nz> wrote:
It's already possible. >>> import sys >>> class foo(object): ... def __getattr__(self, clsname): ... return type(clsname, (object,), {}) ... >>> sys.modules['loader'] = foo() >>> from loader import bar >>> bar <class '__main__.bar'> >>> import loader >>> loader.boo <class '__main__.boo'> >>> - Josiah

Josiah Carlson wrote:
Yes, that's the sort of ugly hack I was talking about (although mine was slightly worse, involving a module replacing itself with a subclass of module and then re-importing itself). I keep thinking there ought to be a neater way, although I haven't figured out exactly what it should look like. -- Greg

"tomer filiba" <tomerfiliba@gmail.com> wrote:
first thing: properties. i prefer this approach to properties (example below). true, it involves some magic, but the magic is very restricted and contained.
[snip] I'm not a big fan of the style that you propose. It doesn't fit my aesthetics. I'd rather introduce another level of indentation with a class statement than to confuse myself with generic-like decoration that aren't actually generics.
I have never made any claim that they were introduced to offer that functionality (incidentally, I don't believe anyone else has claimed as much on this list either), I stated that they *could be used* to offer that functionality, expressed that I had done so, and in my opinion, using them as a generic container was obvious. If others disagree with my opinions, that's fine, but please don't put words into my mouth.
If metaclasses are rarely used by users, then where is the problem of using (and abusing) them if a person desires?
Don't get me wrong, I've been pushing for class decorators for a couple years now (after 2.4 was released without them), and also generally dislike the uglification of metaclass semantics, but every extra argument to 'class foo(<arguments>):' necessarily makes it an uglier mess than it already is. Yes, overloading metaclasses to return a dictionary-like object as a namespace is ugly, but getting the 'order' list in '(name, bases, attrs, order)' to be correct when confronted with 'del' is tricky, and will necessarily require an extra line of boilerplate. Of course whether this is a bigger issue than everyone writing their own ordered dict, is another dicussion (that I don't particularly want to participate in).
Because it offers everything necessary for certain higher order functionality without needing to change the base language. I don't know about others, but I am conservative about language change. I believe that Python should be no simpler and no more complex than necessary. Adding yet another way of defining a namespace (with a namespace construct as you propose) won't offer us anything that we don't already have with 'class namespace'. - Josiah
participants (5)
-
Greg Ewing
-
Josiah Carlson
-
Ron Adam
-
Tal Einat
-
tomer filiba