Carl Banks <pavlovevide...@gmail.com> writes: > On Apr 17, 4:00 pm, Scott David Daniels <scott.dani...@acm.org> wrote: >> Carl Banks wrote: >> > On Apr 17, 10:21 am, J Kenneth King <ja...@agentultra.com> wrote: >> >> Consider: >> >> >> code: >> >> ------------------------------------------------------------------------ >> >> >> class MyInterface(object): >> >> >> def __get_id(self): >> >> return self.__id >> >> >> id = property(fget=__get_id) >> >> >> def __init__(self, id, foo): >> >> self.__id = id >> >> self.foo = foo >> >> >> class MyInterface2(object): >> >> >> def __init__(self, id, foo): >> >> self._id = id >> >> self.foo = foo >> >> >> @property >> >> def id(self): >> >> return self._id >> >> ... >> >> I was recently informed that it was 'unpythonic' and have since been a >> >> little confused by the term. I've heard it bandied about before but >> >> never paid much attention. What is 'unpythonic'? What about this example >> >> is unpythonic? >> >> > There are different reasons someone might have said it. >> > ... >> > Some people think attribute name-mangling is unpythonic. It's true >> > that people sometimes mistakenly treat it a solid information hiding >> > mechanism, but I wouldn't call its usage unpythonic when used as >> > intended: as a way to avoid name-collisions. If you think it's >> > worthwhile to protect an attribute from being overwritten, you might >> > as well guard against accidental conflict with the underlying name. >> >> Here you are assuming that a user of your class could not possibly have a >> valid reason for getting to the underlying variable. Don't make those >> decisions for someone else, in Python, "we are all adults here." > > They can use the demangled name of the internal variable if they want > access to it. > > >> > Finally, some people think read-only attributes are unpythonic. I >> > think that's ridiculous, although in general I'd advise against making >> > attributes read-only willy-nilly. But there's a time and place for >> > it. >> >> Generally, properties are for doing some form of calculation, not >> for making things read-only. > > That might be how properties are "generally" used, but if for some > reason I wanted a read-only attribute, that's how I'd do it. > > > [snip strawman stuff] >> It is not >> your job to protect those users who do not use your code properly from >> themselves; that way lies madness. > > I'm sorry, but the universe is not as simple as you are making it out > to be. Blanket statements like the one you just gave here are not > something that should ever be blindly adhered to. > > If, in my judgment, users would be prone to overwrite one of my > attributes, and if I designed the system to rely on that attribute, > and if the results of changing it are bad enough, then by golly I'm > going to make the attribute harder than usual to modify. And yes, > that is my job. > > Users who want to change it anyway can curse me and then go demangle > the name themselves. > > > Carl Banks
Thanks for all the replies -- While greatly simplified, the reason for desiring read-only attributes in this case is that the interface is to a remote server whose policy relies on data objects represented by this class to have a few values which never change or are managed by the server and not the end user. Changing the ID value would break things on the server, so I wanted to write the interface class to respect those conventions. I'm well aware that if a developer really wanted to, they could get around it no matter what I did, but I figure that if I at least make it really difficult it will be obvious that they're really going into dangerous territory. Further (and this might just be a tad paranoid), user interface code which might use this API might be dangerous. It's one thing for a developer to break the rules when they need to, but a user shouldn't be able to. By enforcing read-only on the API it ensure (at least in my world view) that a developer writing a user interface against it won't have to code defensively against malicious input. However, since the difference between the two is simply attribute name-mangling it's practically a pedantic issue. I guess there might be some hyper-specific scenario where MyInterface would still be useful, but this one might not be it. Again, thanks. :) -- http://mail.python.org/mailman/listinfo/python-list