RE: Making immutable instances
Delaney, Timothy (Tim) [EMAIL PROTECTED] wrote in news:[EMAIL PROTECTED]: Was it *really* necessary to send 4 separate emails to reply to four sections of the same email? Good netiquette is to intersperse your comments with quoted sections in a single email. Tim Delaney Good netiquette might also suggest quoting what you're replying to, wouldn't you think? -- rzed -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] writes: Mike Meyer wrote: [EMAIL PROTECTED] writes: Quoting the frequently used term Practicality beats purity. If I have a practical problem/needs now and it solves it, why not use it ? In other words, you have a use case. Cool. Please tell us what it is - at least if it's better than I think that's bad style. Huh ? I said that if I need immutable instance, I won't hestiate to use __slot__, I didn't say I have a need. A need implies a use case. Yes, you didn't say you had one, you said if, and I jumpted the gun. Lots of people seem to want immutable instances. Nobody seems to have a use case for them. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer [EMAIL PROTECTED] writes: Lots of people seem to want immutable instances. Nobody seems to have a use case for them. What is the use case for immutable strings? Why shouldn't strings be mutable like they are in Scheme? Generally if I know I don't plan to mutate something, I'd want to make it immutable so the runtime system can notice if I make an error. It's like an assert statement spread through the whole program. -- http://mail.python.org/mailman/listinfo/python-list
RE: Making immutable instances
Rick Wotnaz wrote: Good netiquette might also suggest quoting what you're replying to, wouldn't you think? Damn - I trimmed [EMAIL PROTECTED] instead of python-list from the To: list. I stuffed up. This one intentionally sent to python-list. Tim Delaney -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer [EMAIL PROTECTED] wrote: Lots of people seem to want immutable instances. Nobody seems to have a use case for them. Perhaps you missed my release announcement of the 'enum' package that explains why Enum instances are immutable. -- \Hanging one scoundrel, it appears, does not deter the next. | `\ Well, what of it? The first one is at least disposed of. -- | _o__) Henry L. Mencken | Ben Finney -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Paul Rubin http://[EMAIL PROTECTED] writes: Mike Meyer [EMAIL PROTECTED] writes: Lots of people seem to want immutable instances. Nobody seems to have a use case for them. What is the use case for immutable strings? Why shouldn't strings be mutable like they are in Scheme? I don't know. Why shouldn't they? Generally if I know I don't plan to mutate something, I'd want to make it immutable so the runtime system can notice if I make an error. It's like an assert statement spread through the whole program. That's not a use case, that's a debugging aid. The same logic applies to adding type declarations, private/public/etc. declerations, and similar BD language features. It's generally considered that it's not a good enough reason for adding those, so it doesn't really constitute a good enough reason for making an instance immutable. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney [EMAIL PROTECTED] writes: Mike Meyer [EMAIL PROTECTED] wrote: Lots of people seem to want immutable instances. Nobody seems to have a use case for them. Perhaps you missed my release announcement of the 'enum' package that explains why Enum instances are immutable. Yes, I did. I couldn't turn it up in Google, either. I did find a long thread where you discuss the issue. Reading that, I found justifications for having a constant hash value, and having immutable attributes - but I've known about those for a long time.. Neither of these constitutes an immutable instance. Could I get you to recap the reason? thanks, mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: That's not a use case, that's a debugging aid. The same logic applies to adding type declarations, private/public/etc. declerations, and similar BD language features. It's generally considered that it's not a good enough reason for adding those, so it doesn't really constitute a good enough reason for making an instance immutable. By design, this is a don't use feature so it would be very hard to find a use case ;-) I can only think of a situation which may not be able to detect by testing. Say I have a module version 1 which is used by app version 1. In your app, you attach your own attribute to an instance of the module. Everything is fine. Now module becomes version 2 which happens to use the same attribute name that you hang on it and the program starts to behave strangely because they are stepping on each other's foot without knowing it. If everything is done by the same group of people with good communication, it may be possible to detect it. But if the module is done by a third party, and the app is done by yet another third party. The situation becomes complicated. Say if under debian, I do an apt-get python-sqlobject which may be used by multiple apps. If one of them happens to do it this way, this senario may happen. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer [EMAIL PROTECTED] wrote: Ben Finney [EMAIL PROTECTED] writes: Mike Meyer [EMAIL PROTECTED] wrote: Lots of people seem to want immutable instances. Nobody seems to have a use case for them. Perhaps you missed my release announcement of the 'enum' package that explains why Enum instances are immutable. Yes, I did. I couldn't turn it up in Google, either. It was the announcement for enum 0.3: URL:http://groups.google.com/group/comp.lang.python/browse_thread/thread/ea5991de0459d5c4/ Could I get you to recap the reason? Since the values of an enumeration are directly reflected in the values and attributes, Enum instances are immutable to preserve this relationship -- \ I can picture in my mind a world without war, a world without | `\ hate. And I can picture us attacking that world, because they'd | _o__)never expect it. -- Jack Handey | Ben Finney -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] writes: Mike Meyer wrote: That's not a use case, that's a debugging aid. The same logic applies to adding type declarations, private/public/etc. declerations, and similar BD language features. It's generally considered that it's not a good enough reason for adding those, so it doesn't really constitute a good enough reason for making an instance immutable. By design, this is a don't use feature so it would be very hard to find a use case ;-) But I can think of use cases for instances with no mutable attributes, which is another don't use case. If I can do that, those proposing that instances ought to be immutable should be able to come up with a use case. I can only think of a situation which may not be able to detect by testing. Say I have a module version 1 which is used by app version 1. In your app, you attach your own attribute to an instance of the module. Everything is fine. Now module becomes version 2 which happens to use the same attribute name that you hang on it and the program starts to behave strangely because they are stepping on each other's foot without knowing it. If everything is done by the same group of people with good communication, it may be possible to detect it. But if the module is done by a third party, and the app is done by yet another third party. The situation becomes complicated. Say if under debian, I do an apt-get python-sqlobject which may be used by multiple apps. If one of them happens to do it this way, this senario may happen. This is a problem with OO in general, not with not having immutable instances. You get the same problem if, instead of attaching attributes to your instances, I subclass your class and add the attribute in the subclass (which I can do even if both my instances and yours are immutable). In short, immutable instances don't solve your problem, so this doesn't work as a use case. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney [EMAIL PROTECTED] writes: Since the values of an enumeration are directly reflected in the values and attributes, Enum instances are immutable to preserve this relationship This justifies making the attributes immutable. But that's old hat - I had that use case last year. It doesn't justify making the instances immutable. Or if it does, I missed it. thanks, mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: By design, this is a don't use feature so it would be very hard to find a use case ;-) But I can think of use cases for instances with no mutable attributes, which is another don't use case. If I can do that, those proposing that instances ought to be immutable should be able to come up with a use case. Lose you, can you clarify ? This is a problem with OO in general, not with not having immutable instances. You get the same problem if, instead of attaching attributes to your instances, I subclass your class and add the attribute in the subclass (which I can do even if both my instances and yours are immutable). In short, immutable instances don't solve your problem, so this doesn't work as a use case. um, that could be true(already forgot if I can do this in say C++). How would I solve this kind of issue then, just curious. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer [EMAIL PROTECTED] wrote: ... This is a problem with OO in general, not with not having immutable instances. You get the same problem if, instead of attaching attributes to your instances, I subclass your class and add the attribute in the subclass (which I can do even if both my instances So you'd have to make your class non-subclassable -- easy to do when you're implementing a type in C, or with a custom metaclass. I guess that's the motivation behind final classes in Java, btw -- arguably one of the worst enablers of designer hubris, of course;-) Alex -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] writes: Mike Meyer wrote: By design, this is a don't use feature so it would be very hard to find a use case ;-) But I can think of use cases for instances with no mutable attributes, which is another don't use case. If I can do that, those proposing that instances ought to be immutable should be able to come up with a use case. Lose you, can you clarify ? There are lots of use cases where you want your attributes to be immutable. Rationals, enums, anything where you want your instance to contain some used as a value, or usable as a dictionary key that might equal other instances, or - well, you should get the idea. This is a problem with OO in general, not with not having immutable instances. You get the same problem if, instead of attaching attributes to your instances, I subclass your class and add the attribute in the subclass (which I can do even if both my instances and yours are immutable). In short, immutable instances don't solve your problem, so this doesn't work as a use case. um, that could be true(already forgot if I can do this in say C++). How would I solve this kind of issue then, just curious. BD languages have facilities for doing this kind of thing. Alex Martelli has mentioned final classes in Java. C++ and Eiffel let you declare an attribute as not modifiable by subclasses. Eiffel requires that subclasses that override attributes (or methods, for that matter) do so in a type-compatable manner, so you'd probably get a compile error in your subclass in this case. There are certainly methods I've never heard of as well. In Python, you can do things that try and enforce this (I don't know how, because it's not something I think is reasonable to want to do), but the language is also powerful enough that I'd be surprised if they couldn't be defeated in some manner. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer [EMAIL PROTECTED] wrote: Ben Finney [EMAIL PROTECTED] writes: Since the values of an enumeration are directly reflected in the values and attributes, Enum instances are immutable to preserve this relationship This justifies making the attributes immutable. But that's old hat - I had that use case last year. It doesn't justify making the instances immutable. Or if it does, I missed it. The Enum class promises that instances will have all the enumeration values as instance attributes, and that all the instance attributes are values in the enumeration. That requires that the set of attributes on the instance not be changed after creation. -- \ The future always arrives too fast, and in the wrong order. | `\ -- Alvin Toffler | _o__) | Ben Finney -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney [EMAIL PROTECTED] writes: Mike Meyer [EMAIL PROTECTED] wrote: Ben Finney [EMAIL PROTECTED] writes: Since the values of an enumeration are directly reflected in the values and attributes, Enum instances are immutable to preserve this relationship This justifies making the attributes immutable. But that's old hat - I had that use case last year. It doesn't justify making the instances immutable. Or if it does, I missed it. The Enum class promises that instances will have all the enumeration values as instance attributes, and that all the instance attributes are values in the enumeration. That requires that the set of attributes on the instance not be changed after creation. It doesn't say anything about that in the package, and there are no docs in what's I downloaded from PyPI. Doesn't live up to those promises, either. But what's the point of promising that there won't be any attributes that aren't values? Do you expect the user to know how to distinguish implementation details from actual attributes(*), and get a list of value names by filtering them from the attribute list? Wouldn't it be easier to provide a method that returned a tuple of names - at least easier than tuple(value.key for value in myenum)? Sorry if you discussed this in the thread on the enum class, but I didn't follow it. mike *) Actually, the user is required to know implementation details, as otherwise they'll have problems with value names that collide with them. -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Paul Rubin http://[EMAIL PROTECTED] writes: Mike Meyer [EMAIL PROTECTED] writes: Letting the class author declare whether or not the client can add attributes is wrong for the same reasons - and in the same places - that letting the class author declare that the client shouldn't be allowed to access specific attributes, and so on, is wrong. The same logic can apply to what the class operations should do. The answer is the same in both cases. That's why subclassing and inheritance were invented. Exactly. Adding an attribute is isomorphic to subclassing, except it doesn't' take any boilerplate. Unless you do something to prevent people from subclassing, they can always write the boilerplate and pretty much continue as before. I don't believe there's a good reason for preventing the boilerplate free method, and repeated requests for a use case for this have gone unsatisied. Have you got a use case? mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] writes: I am puzzled, and could have read what you want wrong. Are you saying you want something like this : a={} a.something = I want to hang my stuff here, outside the intended use of dict Exactly. For a use case, consider calling select.select on lists of file objects. If the processing is simple enough, the clearest way to associate a handler with each socket is just to add it as an attribute. But that doesn't work - sockets are bulitin types. So you consider less light-weight solutions, like subclassing socket (now that that's possible), or a dictionary of handlers keyed by socket. This works by default with classes written in Python. That it doesn't work for builtins is inconsistent, non-orthogonal, and incomplete. However, it's easy to work around, and the obvious fix - adding a dictionary to every builtin - is rather costly. So we'll live with it since practicality beats purity. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: [EMAIL PROTECTED] writes: I am puzzled, and could have read what you want wrong. Are you saying you want something like this : a={} a.something = I want to hang my stuff here, outside the intended use of dict Exactly. For a use case, consider calling select.select on lists of file objects. If the processing is simple enough, the clearest way to associate a handler with each socket is just to add it as an attribute. But that doesn't work - sockets are bulitin types. So you consider less light-weight solutions, like subclassing socket (now that that's possible), or a dictionary of handlers keyed by socket. This works by default with classes written in Python. That it doesn't work for builtins is inconsistent, non-orthogonal, and incomplete. However, it's easy to work around, and the obvious fix - adding a dictionary to every builtin - is rather costly. So we'll live with it since practicality beats purity. While I agree with the use case(I want it sometimes too), it seems that the language creator may also deliberately disallow that, not because it is not doable or costly. So how, the built-in types still need to have some form of dictionary or else how would dir(a) of the above dictionary work ? -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] writes: Mike Meyer wrote: [EMAIL PROTECTED] writes: I am puzzled, and could have read what you want wrong. Are you saying you want something like this : a={} a.something = I want to hang my stuff here, outside the intended use of dict Exactly. For a use case, consider calling select.select on lists of file objects. If the processing is simple enough, the clearest way to associate a handler with each socket is just to add it as an attribute. But that doesn't work - sockets are bulitin types. So you consider less light-weight solutions, like subclassing socket (now that that's possible), or a dictionary of handlers keyed by socket. This works by default with classes written in Python. That it doesn't work for builtins is inconsistent, non-orthogonal, and incomplete. However, it's easy to work around, and the obvious fix - adding a dictionary to every builtin - is rather costly. So we'll live with it since practicality beats purity. While I agree with the use case(I want it sometimes too), it seems that the language creator may also deliberately disallow that, not because it is not doable or costly. So how, the built-in types still need to have some form of dictionary or else how would dir(a) of the above dictionary work ? Built-in types don't have a real dictionary. They have a C struct that holds the various methods. The entries in the struct are called slots, hence the __slots__ magic attribute. That __slots__ makes it impossible to add an attribute is documented as an implementation detail. This makes me think that the same restriction on the builtin types is the same. FWIW, dir returns a list built from a number of source. But if you look at, for example, list.__dict__, you'll notice that it's not a dict. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: Built-in types don't have a real dictionary. They have a C struct that holds the various methods. The entries in the struct are called slots, hence the __slots__ magic attribute. That __slots__ makes it impossible to add an attribute is documented as an implementation detail. This makes me think that the same restriction on the builtin types is the same. FWIW, dir returns a list built from a number of source. But if you look at, for example, list.__dict__, you'll notice that it's not a dict. Well, in this case, would it be simple for the OP that if he wants to disallow this attaching additional things, just use __slot__. What I wan to say though is, if we can live with the inability of not able to attach to built-in types, why is it so difficult for other user defined class ? If the authors go to the length of not allowing it, so be it. They are afterall define it for their use and how someone else will use it don't matter. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] writes: Well, in this case, would it be simple for the OP that if he wants to disallow this attaching additional things, just use __slot__. That's *documented* as an implementation-dependent behavior. Using it to get that effect is abuse of the feature, and may well quit working in the future. What I wan to say though is, if we can live with the inability of not able to attach to built-in types, why is it so difficult for other user defined class ? Because not being able to do it for built-in types is an implementation detail, and a wart in the language. And again, *what's the use case*? A number of people have asked why we shouldn't allow this, but none of them been able to come up with a use case better than I think doing that is bad style. If the authors go to the length of not allowing it, so be it. They are afterall define it for their use and how someone else will use it don't matter. I take it you never distribute your code, or otherwise expect other people to reuse it? mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: If the authors go to the length of not allowing it, so be it. They are afterall define it for their use and how someone else will use it don't matter. I take it you never distribute your code, or otherwise expect other people to reuse it? No, distribute when necessary. But I define it and code it the way I want, how and others will use it, curse it doesn't matter to me. Of course, I would give suggestion(wish list bug as in debian term) when I use other people's stuff, and see a particular usage that is not there. But it ends just there, wish list. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: [EMAIL PROTECTED] writes: Well, in this case, would it be simple for the OP that if he wants to disallow this attaching additional things, just use __slot__. That's *documented* as an implementation-dependent behavior. Using it to get that effect is abuse of the feature, and may well quit working in the future. In this case, it seems to be fine. As the intend is just not allowing. Even it changes in the future, the worst case is just allowing, that fits your needs :-) It still won't affect what is working, so it is harmless side effect, if it ever changes in the future. Abuse or not doesn't matter so long it fits the needs, IMO. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: [EMAIL PROTECTED] writes: Well, in this case, would it be simple for the OP that if he wants to disallow this attaching additional things, just use __slot__. That's *documented* as an implementation-dependent behavior. Using it to get that effect is abuse of the feature, and may well quit working in the future. I don't see it mention as implementation-dependent behaviour on this page, and this is supposed to be (for language lawyers). http://www.python.org/doc/2.4.2/ref/slots.html If it really is implementation detail but not a binding to the language feature, I think someone need to change the doc, at least make it more clear on this page. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: And again, *what's the use case*? A number of people have asked why we shouldn't allow this, but none of them been able to come up with a use case better than I think doing that is bad style. oh, that is the usual argument anyway. It is nothing but style, most of the time. Making a style thing into a right/wrong, better/worse argument is really for time killing, there would never be real answer. -- http://mail.python.org/mailman/listinfo/python-list
RE: Making immutable instances
Was it *really* necessary to send 4 separate emails to reply to four sections of the same email? Good netiquette is to intersperse your comments with quoted sections in a single email. Tim Delaney -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] writes: Mike Meyer wrote: [EMAIL PROTECTED] writes: Well, in this case, would it be simple for the OP that if he wants to disallow this attaching additional things, just use __slot__. That's *documented* as an implementation-dependent behavior. Using it to get that effect is abuse of the feature, and may well quit working in the future. It still won't affect what is working, so it is harmless side effect, if it ever changes in the future. If not allowing is required, then allowing is not working, pretty much by definition. Abuse or not doesn't matter so long it fits the needs, IMO. I guess it doesn't matter to you whether or not your code works in the future. It does to me. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: [EMAIL PROTECTED] writes: Mike Meyer wrote: [EMAIL PROTECTED] writes: Well, in this case, would it be simple for the OP that if he wants to disallow this attaching additional things, just use __slot__. That's *documented* as an implementation-dependent behavior. Using it to get that effect is abuse of the feature, and may well quit working in the future. It still won't affect what is working, so it is harmless side effect, if it ever changes in the future. If not allowing is required, then allowing is not working, pretty much by definition. Abuse or not doesn't matter so long it fits the needs, IMO. I guess it doesn't matter to you whether or not your code works in the future. It does to me. For this particular case, I don't see it as a problem. First it meets the need, works on 2.2, 2.3, 2.4. No one knows what would change in the future, beside the fact that I don't see it as implementation-dependent in the doc. Adding to the fact that things can/may be removed even it is fully documented, without this caveat emptor(like the famous reduce/map etc.). That is if I read the document when I was writing python codes in the early days and used reduce/map/filter/lambda, my code still breaks if in one day those are removed and I can't forsee that either. So why bother, unless it has some definitive schedule(like saying in 2.5, reduce won't be there or __slot__ behaviour will definitely change), then I would consider if the code I write now should avoid using it. And back to this case, I regard it as a no harm side effect, yes, it doesn't perform as expected(assume it really is changed in some unknown version in the future) that someone does hang something there, it doesn't hurt my expected usage of the class, as this is used to prevent unexpected usage. Quoting the frequently used term Practicality beats purity. If I have a practical problem/needs now and it solves it, why not use it ? The zip(it,it) case is even worse than this __slot__ situation and I don't have much problem in using that either. It is not unusual in this industry that certain software only expects to be working with some combination of OS/Compiler version. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] writes: Quoting the frequently used term Practicality beats purity. If I have a practical problem/needs now and it solves it, why not use it ? In other words, you have a use case. Cool. Please tell us what it is - at least if it's better than I think that's bad style. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: [EMAIL PROTECTED] writes: Quoting the frequently used term Practicality beats purity. If I have a practical problem/needs now and it solves it, why not use it ? In other words, you have a use case. Cool. Please tell us what it is - at least if it's better than I think that's bad style. Huh ? I said that if I need immutable instance, I won't hestiate to use __slot__, I didn't say I have a need. In other words, I see __slot__ as a solution to the problem, I am not saying I have the problem in the first place. The practicabilty beats purity is used to support this using __slot__ situation, not about the need of immutable instance. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer [EMAIL PROTECTED] writes: When it was suggested that a facility for doing this be added to the language, I asked for a use case for it. Nobodies come up with a reason for placing such restriction on the client yet. If you've got a use case, I'd be interested in hearing it. I see it the other way; almost all the time in my own code I try to initialize all of any instance's attributes in an __init__ method. Dynamically adding attributes is useful sometimes, but done willy-nilly leads to spaghetti code. In the cases where it's useful, I'd rather see it done through a special __setattr__ method, perhaps inherited from a mixin: class Frob(Whatsit, DynamicAttributeMixin): ... However, that's not likely to happen. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Paul Rubin http://[EMAIL PROTECTED] writes: Mike Meyer [EMAIL PROTECTED] writes: When it was suggested that a facility for doing this be added to the language, I asked for a use case for it. Nobodies come up with a reason for placing such restriction on the client yet. If you've got a use case, I'd be interested in hearing it. I see it the other way; almost all the time in my own code I try to initialize all of any instance's attributes in an __init__ method. Dynamically adding attributes is useful sometimes, but done willy-nilly leads to spaghetti code. Pretty much anything, if abused, can lead to spaghetti code. In the cases where it's useful, I'd rather see it done through a special __setattr__ method, perhaps inherited from a mixin: class Frob(Whatsit, DynamicAttributeMixin): ... However, that's not likely to happen. The thing is, the need for an extra attribute doesn't come from your class, it comes from the client of your class. You can't know if the client code will need that facility or not, so the only choice you know won't be wrong sometime is to always add the mixin. In which case, you should follow the Python the less boilerplate, the better practice, and leave it off. Which is what we have. Letting the class author declare whether or not the client can add attributes is wrong for the same reasons - and in the same places - that letting the class author declare that the client shouldn't be allowed to access specific attributes, and so on, is wrong. Of course, it's also *right* for the same reasons and in the same places as those things. I just don't think those places happen in Python programs. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer [EMAIL PROTECTED] writes: Letting the class author declare whether or not the client can add attributes is wrong for the same reasons - and in the same places - that letting the class author declare that the client shouldn't be allowed to access specific attributes, and so on, is wrong. The same logic can apply to what the class operations should do. The answer is the same in both cases. That's why subclassing and inheritance were invented. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: The thing is, the need for an extra attribute doesn't come from your class, it comes from the client of your class. You can't know if the client code will need that facility or not, so the only choice you know won't be wrong sometime is to always add the mixin. In which case, you should follow the Python the less boilerplate, the better practice, and leave it off. Which is what we have. Letting the class author declare whether or not the client can add attributes is wrong for the same reasons - and in the same places - that letting the class author declare that the client shouldn't be allowed to access specific attributes, and so on, is wrong. Of course, it's also *right* for the same reasons and in the same places as those things. I just don't think those places happen in Python programs. I am puzzled, and could have read what you want wrong. Are you saying you want something like this : a={} a.something = I want to hang my stuff here, outside the intended use of dict -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Op 2005-11-26, Steven D'Aprano schreef [EMAIL PROTECTED]: On Thu, 24 Nov 2005 12:55:07 +, Antoon Pardon wrote: Suppose I have the following code. from module import __take_care__ __private_detail__ = ... I now have two variable that are flaged the same way, but they are not. No, you have two names written using a poor naming convention. Well if it is a poor naming convention, why react to me, and not to Mike who was defending this poor naming convention? __name__ should be used only for Python's special methods. __take_care__ is a private variable from an other module which I should use with extreme care not to break the other package. Python doesn't do any special treatment of __name or __name__ from modules. The only information hiding techniques Python enforces are that module._name (single leading underscore) is not imported by from module import *, and class.__name (double leading underscore) is mangled to class._Class__name. We were not talkin about special treatment by python. We were talking about conventions to communicate purpose to other readers of the software. It are other modules that should take special care if they should choose to import this variable. I'm not sure what the difference is. If there is a difference, why are you using the same naming convention for different sorts of names (private module variable and private module data). If there is no difference, I don't understand the point of your example. Well it seems you didn't seem to understand the point of my answer. Maybe you should first reread the article I responded too. -- Antoon Pardon -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
On Fri, 25 Nov 2005 23:20:05 -0500, Mike Meyer wrote: Steven D'Aprano [EMAIL PROTECTED] writes: Hmmm, the class designer didn't want me adding attributes to instances... maybe he had a good reason for that... When it was suggested that a facility for doing this be added to the language, I asked for a use case for it. Nobodies come up with a reason for placing such restriction on the client yet. Oh, I think it is terribly unfair to call them nobodies, even if you don't like their use-cases *grin* If you've got a use case, I'd be interested in hearing it. frozenset perhaps? If it were needed once, it could be needed again. The obvious case would be for a class where distinct instances that compare equal but not identical map to the same value in a dict. In any case, I'm not the one claiming that I need custom immutable classes. I'm just suggesting that there is nothing non-Pythonic about them. If Ben thinks he needs them, I'm sure he has put *far* more thought into it than I have. I know Ben in RL, and he is not someone to make snap judgements about turning Python into Some Other Language Just Because. -- Steven. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Steven D'Aprano [EMAIL PROTECTED] writes: On Fri, 25 Nov 2005 23:20:05 -0500, Mike Meyer wrote: If you've got a use case, I'd be interested in hearing it. frozenset perhaps? If it were needed once, it could be needed again. That's not a use case, that's an example. And not a very good one, as it's not at all clear that the restriction is intentional in that case. After all, the same restriction applies to every builtin type, including the mutable version of frozenset. The obvious case would be for a class where distinct instances that compare equal but not identical map to the same value in a dict. How does the ability to add attributes to the instances of the class change that behavior? In any case, I'm not the one claiming that I need custom immutable classes. I'm just suggesting that there is nothing non-Pythonic about them. If Ben thinks he needs them, I'm sure he has put *far* more thought into it than I have. I know Ben in RL, and he is not someone to make snap judgements about turning Python into Some Other Language Just Because. I claim that the dynamic natture of Python - which is exemplified by things like duck typing and the ability to add attributes to nearly everything on the fly - is a fundamental part of what makes Python Python. The best reason Ben could come up with is that it makes finding bugs a bit easier. But so do type declarations, static namespaces, private and protected attributes, and a slew of similar BD features that are pretty much anathema to dynamic languages. This feature fits *very* well in languages that have those features, and poorly in languages that reject them, which includes Python. Of course, that a feature has a lot in common with features from un-Pythonic languages doesn't make it ipso facto unPythonic. After all, practicality beats purity. So what's the practical application for such a feature? What's the use case? mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
On Sat, 26 Nov 2005 04:59:59 -0500, Mike Meyer wrote: Steven D'Aprano [EMAIL PROTECTED] writes: On Fri, 25 Nov 2005 23:20:05 -0500, Mike Meyer wrote: If you've got a use case, I'd be interested in hearing it. frozenset perhaps? If it were needed once, it could be needed again. That's not a use case, that's an example. Fine. I want to use a set as a dictionary key, but dict keys must be immutable. And not a very good one, as it's not at all clear that the restriction is intentional in that case. After all, the same restriction applies to every builtin type, including the mutable version of frozenset. Every builtin type, including mutable sets, is immutable??? I think we're talking at cross purposes. I'm talking about immutable instances. What are you talking about? The obvious case would be for a class where distinct instances that compare equal but not identical map to the same value in a dict. How does the ability to add attributes to the instances of the class change that behavior? Er, who said it did? In any case, I'm not the one claiming that I need custom immutable classes. I'm just suggesting that there is nothing non-Pythonic about them. If Ben thinks he needs them, I'm sure he has put *far* more thought into it than I have. I know Ben in RL, and he is not someone to make snap judgements about turning Python into Some Other Language Just Because. I claim that the dynamic natture of Python - which is exemplified by things like duck typing and the ability to add attributes to nearly everything on the fly - is a fundamental part of what makes Python Python. I can't disagree with you there. The best reason Ben could come up with is that it makes finding bugs a bit easier. Are you sure that was Ben? Maybe I missed it. But so do type declarations, static namespaces, private and protected attributes, and a slew of similar BD features that are pretty much anathema to dynamic languages. This feature fits *very* well in languages that have those features, and poorly in languages that reject them, which includes Python. Perhaps. But I don't object to *mild* BD, the sort you can get out of relatively easily. You know, handcuffs, maybe a few ropes, but not lock-them-up-in-the-oubliette-and-throw-away-the-key *wink* All joking aside, I think having immutable custom classes, with or without restricting attribute creation, is no worse than (say) Python's name mangling. Of course, that a feature has a lot in common with features from un-Pythonic languages doesn't make it ipso facto unPythonic. After all, practicality beats purity. So what's the practical application for such a feature? What's the use case? Class instances match by identity when used as keys, not equality. That's over-strict: why should Parrot(Norwegian Blue) map to a different item from Parrot(Norwegian + Blue) just because the first instance has a different memory location to the second? Please note, I do not expect -- and would not want -- the default behaviour to change. Most class instances presumably should be mutable, and therefore mapping by ID is the right behaviour. But some class instances shouldn't be mutable, and should match as keys by equality not identity: we would expect Fraction(num=1, den=2) to match Fraction(num=2, den=4) as a key. -- Steven. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Steven D'Aprano [EMAIL PROTECTED] writes: On Sat, 26 Nov 2005 04:59:59 -0500, Mike Meyer wrote: Steven D'Aprano [EMAIL PROTECTED] writes: On Fri, 25 Nov 2005 23:20:05 -0500, Mike Meyer wrote: If you've got a use case, I'd be interested in hearing it. frozenset perhaps? If it were needed once, it could be needed again. That's not a use case, that's an example. Fine. I want to use a set as a dictionary key, but dict keys must be immutable. Except that dict keys don't have to be immutable. The docs say (or imply) that, but they're wrong. We're discussing new wording in another thread. And not a very good one, as it's not at all clear that the restriction is intentional in that case. After all, the same restriction applies to every builtin type, including the mutable version of frozenset. Every builtin type, including mutable sets, is immutable??? No. I think you missed the entire second half the thread. I think we're talking at cross purposes. I'm talking about immutable instances. What are you talking about? I'm talking about being able to add attributes to an instance. You can't add an attribute to *any* builtin type. This is an implementation detail. I consider it to be a wart in the language, but an acceptable one, because the costs of fixing it are much worse than the costs of working around it, and practicality beats purity. The obvious case would be for a class where distinct instances that compare equal but not identical map to the same value in a dict. How does the ability to add attributes to the instances of the class change that behavior? Er, who said it did? You did. We're looking for a use case for adding the ability to mark a class as having instances that you can't add an attribute to. You suggested this as such a use case. The best reason Ben could come up with is that it makes finding bugs a bit easier. Are you sure that was Ben? Maybe I missed it. No, I'm no sure it was Ben - I didn't go chase down the reference. It's the best use case *from anyone* so far, though. All joking aside, I think having immutable custom classes, with or without restricting attribute creation, is no worse than (say) Python's name mangling. There are well-defined facilities for creating read-only attributes. Is there a difference between an immutable object you can add attributes to, and an object that has nothing but read-only attributes? Of course, that a feature has a lot in common with features from un-Pythonic languages doesn't make it ipso facto unPythonic. After all, practicality beats purity. So what's the practical application for such a feature? What's the use case? Class instances match by identity when used as keys, not equality. That's over-strict: why should Parrot(Norwegian Blue) map to a different item from Parrot(Norwegian + Blue) just because the first instance has a different memory location to the second? Uh - HTH did we get here? Please note, I do not expect -- and would not want -- the default behaviour to change. Most class instances presumably should be mutable, and therefore mapping by ID is the right behaviour. The default behavior is right for in many cases. For those that it's not right, you can fix it. Proper definition of the Parrot class will insure that Parrot(Norwegian Blue) == Parrot(Norwegian + Blue) always evaluates to True. But some class instances shouldn't be mutable, and should match as keys by equality not identity: we would expect Fraction(num=1, den=2) to match Fraction(num=2, den=4) as a key. And you can do that with Python as it exists today (and one of these days I'll get back to my Rational class that does that...). There's no need for any changes to the language to deal with this case. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer [EMAIL PROTECTED] writes: There isn't a standard serialize method in Python, so I don't know how you want to define it. Well, consider pickle, for example. I can think of perfectly reasonable definitions of serialize where obj.serialize() won't always return the same string on an immutable object, even if you don't allow adding attributes. Fair enough. How's this: a = ImmutableObject() b = deepcopy(a) assert a == b # a and b start out equal do stuff # since a and b are immutable, they should still be equal # no matter what has happened above assert a == b If you've added attributes to a but not to b, they should compare unequal, breaking immutability. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Paul Rubin wrote: Fair enough. How's this: a = ImmutableObject() b = deepcopy(a) assert a == b # a and b start out equal do stuff # since a and b are immutable, they should still be equal # no matter what has happened above assert a == b If you've added attributes to a but not to b, they should compare unequal, breaking immutability. How about this ? a=(1,[]) b=copy.deepcopy(a) assert a==b # True a[1].append(1) assert a!=b -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Paul Rubin http://[EMAIL PROTECTED] writes: Mike Meyer [EMAIL PROTECTED] writes: There isn't a standard serialize method in Python, so I don't know how you want to define it. I can think of perfectly reasonable definitions of serialize where obj.serialize() won't always return the same string on an immutable object, even if you don't allow adding attributes. Fair enough. How's this: a = ImmutableObject() b = deepcopy(a) assert a == b # a and b start out equal do stuff # since a and b are immutable, they should still be equal # no matter what has happened above assert a == b If you've added attributes to a but not to b, they should compare unequal, breaking immutability. Why should they compare unequal just because you add an attribute? Nothing says all attributes have to be involved in an equality comparison. In fact, Python classes by default ignore all attributes when doing an equality comparison. In order to compare attributes, you have to provide an __eq__ method (or __cmp__, but we'll ignore that). It can't mention your new attribute, because it doesn't exist unless you add it. So your final assertion will be true even after adding a new attribute. Of course, there's a fundamental flaw in your definition of immutable, in that there are immutable objects - tuples - for which the condition t1 == t2 is *not* a constant. Tuples can hold mutable objects, meaning you can change those. Doing so will make a tuple not compare equal to a copy of the state prior to changing the contents of the tuple. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
On Thu, 24 Nov 2005 12:55:07 +, Antoon Pardon wrote: Suppose I have the following code. from module import __take_care__ __private_detail__ = ... I now have two variable that are flaged the same way, but they are not. No, you have two names written using a poor naming convention. __name__ should be used only for Python's special methods. __take_care__ is a private variable from an other module which I should use with extreme care not to break the other package. Python doesn't do any special treatment of __name or __name__ from modules. The only information hiding techniques Python enforces are that module._name (single leading underscore) is not imported by from module import *, and class.__name (double leading underscore) is mangled to class._Class__name. Both techniques are done in order to let the module creator protect users from *accidentally* shooting themselves in the foot, while still allowing the module users to *deliberately* shoot themselves in the foot if that is what they need or want to do. Deliberately breaking these information hiding techniques are features, not bugs. __private_detail__ on the other hand is just keeping private data for my own module, which I should care about as just any other variable in my module. If you care about keeping __private_detail__ no more than you care about public_detail, what makes one private and one public? It are other modules that should take special care if they should choose to import this variable. I'm not sure what the difference is. If there is a difference, why are you using the same naming convention for different sorts of names (private module variable and private module data). If there is no difference, I don't understand the point of your example. -- Steven. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
On Thu, 24 Nov 2005 11:44:16 -0500, Mike Meyer wrote: In Python, I can even fix it so *your* code uses my wrapped version: import Finney class Addable(Finnney.Immutable): pass Finney.Immutable = Addable Which means that from now on *your* code that tries to create Immutables will actually get Addables. The inability to do this in BD languages is - well, painfull. That Python doesns't require the boilerplate in a good thing. The ability to shoot yourself in the foot *if you want to* is a feature, not a bug. But the ability to shoot yourself in the foot *accidentally* is not a feature. I am happy that whatever restrictions the class designer builds on their class is easy to bypass, because the class designer is not omniscient and their private data may be just the thing I need to solve a problem some day. But I should have to *think about it* before messing about with it. Python's consenting adults philosophy allows the class designer some limited ability to force the class user to think about it before messing about with private variables. I think Ben's immutable class falls into that same category. -- Steven. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Steven D'Aprano [EMAIL PROTECTED] writes: On Thu, 24 Nov 2005 11:44:16 -0500, Mike Meyer wrote: In Python, I can even fix it so *your* code uses my wrapped version: import Finney class Addable(Finnney.Immutable): pass Finney.Immutable = Addable Python's consenting adults philosophy allows the class designer some limited ability to force the class user to think about it before messing about with private variables. I think Ben's immutable class falls into that same category. If you read the whole thread, you'll see that I don't have a problem with messing with private variables. It's disallowing the addition of new variables that I found objectionable. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
On Fri, 25 Nov 2005 20:50:41 -0500, Mike Meyer wrote: Steven D'Aprano [EMAIL PROTECTED] writes: On Thu, 24 Nov 2005 11:44:16 -0500, Mike Meyer wrote: In Python, I can even fix it so *your* code uses my wrapped version: import Finney class Addable(Finnney.Immutable): pass Finney.Immutable = Addable Python's consenting adults philosophy allows the class designer some limited ability to force the class user to think about it before messing about with private variables. I think Ben's immutable class falls into that same category. If you read the whole thread, you'll see that I don't have a problem with messing with private variables. It's disallowing the addition of new variables that I found objectionable. But you've just demonstrated that those who really want to shoot themselves in the foot, er, add new attributes (not variables, let's get the terminology right) can do so by sub-classing and rebinding. The fact that Ben's proposal would prevent you from adding attributes is precisely analogous to the name mangling that Python does: if you want to work around it, it is easy to do so, but you have to make a conscious effort to do so it. Hmmm, the class designer didn't want me adding attributes to instances... maybe he had a good reason for that... -- Steven. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Steven D'Aprano [EMAIL PROTECTED] writes: Hmmm, the class designer didn't want me adding attributes to instances... maybe he had a good reason for that... When it was suggested that a facility for doing this be added to the language, I asked for a use case for it. Nobodies come up with a reason for placing such restriction on the client yet. If you've got a use case, I'd be interested in hearing it. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: If it's not a wart, why would it be a wart for user-defined types to have the same behaviour? It's a wart because user-defined classes *don't* have the same behavior. Then *my* solution for this would be to give user-defined classes a way to behave like builtins, eg. explicitally and fully implement immutability. Immutability is an important concept in Python programs, and I'm impressed it does not have explicit support. -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike wrote: How can a (user-defined) class ensure that its instances are immutable, like an int or a tuple, without inheriting from those types? What caveats should be observed in making immutable instances? IMHO, this is usually (but not always) a mistake. (If you're programming a missle guidance system, or it makes your program go faster it's not a mistake :)) So are PRIVATE, CONST (all types), SEALED, FINAL, etc -- even the best programmer doesn't foresee what a user will want to do to make best use of his components, and many a time I've been annoyed (in Java and MS frameworks) by not being able to access/modify/subclass a member/class that I know is there because it has to be there (or because I can see it in the debugger), but it's not accessable because the programmer was overly clever and had been to OOP school. There's a big difference. An immutable object has a totally different semantic, compared to a mutable object. If you document it to be immutable, and maybe even provide __eq__ /__hash__, adding attributes from it is surely an user bug. And surely a bug for which I'd expect an exception to be raised. Sometimes, I play with some of my objects and I have to go back and check documentation whether they are immutable or not, to make sure I use the correct usage pattern. That's fine, this is what docs are for, but couldn't Python give me some way to enforce this so that, if I or some other dev do the mistake, it doesn't go unnoticed? -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] [EMAIL PROTECTED] wrote: ... qualification, you're quite likely to get such disclaimers. If you don't want them, learn to ask about stopping your users from ACCIDENTALLY doing X, and no reasonable respondant will fail to notice the qualification. Interestingly, that is what I read from the OP, even without the ACCIDENTALLY. While I followed the maxim in the face of ambiguity, refuse the temptation to guess and didn't put words in his mouth that he had in fact not said: I explained what he could do, and how that wouldn't work IF he did NOT mean ``accidentally''. Not sure if this refusal to assume that the requests are _necessarily_ sensible comes from my several years of experience fielding question in this and other newsgroups, or my even more years of experience as a consultant, both freelance and in-house within large organizations... Alex -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Alex Martelli wrote: [EMAIL PROTECTED] [EMAIL PROTECTED] wrote: ... qualification, you're quite likely to get such disclaimers. If you don't want them, learn to ask about stopping your users from ACCIDENTALLY doing X, and no reasonable respondant will fail to notice the qualification. Interestingly, that is what I read from the OP, even without the ACCIDENTALLY. While I followed the maxim in the face of ambiguity, refuse the temptation to guess and didn't put words in his mouth that he had in fact not said: I explained what he could do, and how that wouldn't work IF he did NOT mean ``accidentally''. Not sure if this refusal to assume that the requests are _necessarily_ sensible comes from my several years of experience fielding question in this and other newsgroups, or my even more years of experience as a consultant, both freelance and in-house within large organizations... I fully understand that, in the formal life. But I usually lax that on occasions like here. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: Giovanni Bajo [EMAIL PROTECTED] writes: Mike Meyer wrote: Note that this property of __slots__ is an implementation detail. You can't rely on it working in the future. I don't rely on it. I just want to catch bugs in my code. I certainly hope you're not relying on it to catch bugs. You should do proper testing instead. Not only will that catch pretty much all the bugs you mention later - thus resolving you of the need to handcuff clients of your class - it will catch lots of other bugs as well. That is an ideal case and we all know the real world is not ideal or every program would be bug free. And I don't think anyone would solely relies on the language feature for spotting bugs. Whether this kind of guard is useful is another story. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Giovanni Bajo [EMAIL PROTECTED] writes: Mike Meyer wrote: Note that this property of __slots__ is an implementation detail. You can't rely on it working in the future. I don't rely on it. I just want to catch bugs in my code. I certainly hope you're not relying on it to catch bugs. You should do proper testing instead. Not only will that catch pretty much all the bugs you mention later - thus resolving you of the need to handcuff clients of your class - it will catch lots of other bugs as well. I'm curious as to why you care if people add attributes to your immutable class. Personally, I consider that instances of types don't let me add attributes to be a wart. To catch stupid bugs, typos and whatnot. If an instance is immutable, you can't modify it, period. If you do it, it's a bug. So why not have the bug raises an exception, rather than go unnoticed? It's only a bug if you didn't mean to do it. If you meant to do it, you're taking advantage of a powerful feature of Python. If you feel the need to restrict the use of such features, maybe you should consider a less powerful language? There are lots of languages around that prevent accidental creation of attributes - and lots of other similar usages that are bugs if you don't mean to do them. I don't see your point, either. Why would you want to add attributes to an object documented to be immutable? The documentation is immaterial. The *need* is what's important. I've had use cases were some object was almost exactly what I wanted, except I needed another bit of data dragged along. Python lets me do that for most classes, which is one of the things that I like about it - it doesn't handcuff me. If it's not a wart, why would it be a wart for user-defined types to have the same behaviour? It's a wart because user-defined classes *don't* have the same behavior. Then *my* solution for this would be to give user-defined classes a way to behave like builtins, eg. explicitally and fully implement immutability. Well, if you want to propose a change to the language, you need a good use case to demonstrate the benefits of such a change. Do you have such a use case? Catching bugs doesn't qualify, otherwise Python would be radically different from what it is. Immutability is an important concept in Python programs, and I'm impressed it does not have explicit support. I'm not convinced that immutability is that important a concept. Yeah, you have to know about it, but it seems more like an implementation detail than a crucial concept. I'm not sure it's more important than things like interned strings and the sharing of small integers. Most of the discussion of immutables here seems to be caused by newcomers wanting to copy an idiom from another language which doesn't have immutable variables. Their real problem is usually with binding, not immutability. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Op 2005-11-24, Mike schreef [EMAIL PROTECTED]: Ben Finney [EMAIL PROTECTED] wrote in message news:[EMAIL PROTECTED] Howdy all, How can a (user-defined) class ensure that its instances are immutable, like an int or a tuple, without inheriting from those types? What caveats should be observed in making immutable instances? IMHO, this is usually (but not always) a mistake. (If you're programming a missle guidance system, or it makes your program go faster it's not a mistake :)) So are PRIVATE, CONST (all types), SEALED, FINAL, etc -- even the best programmer doesn't foresee what a user will want to do to make best use of his components, But maybe what the user wants no longer guarantees correct working. and many a time. I've been annoyed (in Java and MS christelijke vorm er van. frameworks) by not being able to access/modify/subclass a member/class that I know is there because it has to be there (or because I can see it in the debugger), Maybe that it is there is just an implementation detail. but it's not accessable because the programmer was overly clever and had been to OOP school. I think hiding something that is essentially an implementation detail is good abstraction and programming practice. A fine-grained capability architecture married to the language and runtime where I can declare my own level cleverness to override the programmer's would be nice, but I think Python's voluntary DoThis, _DoThisIfYouReallyHaveTo, and __You'dBetterKnowWhatYou'reDoing__ approach is a better way to go than the undefeatable keyword approach. I disagree. Suppose I have the following code. from module import __take_care__ __private_detail__ = ... I now have two variable that are flaged the same way, but they are not. __take_care__ is a private variable from an other module which I should use with extreme care not to break the other package. __private_detail__ on the other hand is just keeping private data for my own module, which I should care about as just any other variable in my module. It are other modules that should take special care if they should choose to import this variable. That is why I don't think the underscore prefixes are very usefull. They constantly flag to take care with a specific variable, while that variable is nothing special within the module itself. -- Antoon Pardon -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney wrote: Alex Martelli [EMAIL PROTECTED] wrote: Ben Finney [EMAIL PROTECTED] wrote: How can a (user-defined) class ensure that its instances are immutable, like an int or a tuple, without inheriting from those types? You can make a good start by defining __setattr__, __delattr__ (and __setitem__ and __delitem__ if your class is a container) to raise exceptions. Remember that your redefined __setattr__ IS in place even when you're initializing your istance, so remember to delegate attribute setting to the superclass (the other special methods mentioned above are less likely to byte you). So, for a class that needs to set attributes in __init__ (but after that, become immutable), how do I get around this? Should I make a _FooFunctionality class, and then inherit from that to make Foo as the immutable class that actually gets exported? Typically, constants are set up in __new__ (which happens before __init__), because by __init__ time the object is built. Remember not to complain that you have no copy operation, because there is no such thing as a copy of a constant (the original constant is good enough). --Scott David Daniels [EMAIL PROTECTED] -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Alex Martelli [EMAIL PROTECTED] wrote: Ben Finney [EMAIL PROTECTED] wrote: Why is I want to make objects immutable seen as I don't trust my users? Are Python's existing immutable types also seen the same way? If not, why the distinction? A type implemented in C offers different possibilities than one implemented in Python -- no deep conceptual reason, just practical ones. So, in the hypothetical situation that all Python types were implemented in pure Python, what would the ideal behaviour for immutables be? Or would there be no immutables? I don't think that making it explicit that you intended to document the restriction would have changed my answer (although an explicit acknowlegment that you're looking for restrictions against accidental misuse rather than against determined attackers surely would). I'm looking for a consenting adults restriction: classes will have immutable instances only where it makes sense from the class protocol. I'm not going to lose sleep over users who go looking for trouble. -- \ Think for yourselves and let others enjoy the privilege to do | `\ so too. -- Voltaire, _Essay On Tolerance_ | _o__) | Ben Finney -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Antoon Pardon wrote: Op 2005-11-24, Mike schreef [EMAIL PROTECTED]: and many a time. I've been annoyed (in Java and MS christelijke vorm er van. frameworks) Antoon, I don't think Mike wrote it like that :) I don't even know how I spotted that, since I didn't really read that part of the text. I guess the Dutch words caught my attention somehow. It even took a while for me to realize that it must have been an error; the first few seconds I was trying to find the relationship between christianity and Java, MS or frameworks. Without success, obviously. -- If I have been able to see further, it was only because I stood on the shoulders of giants. -- Isaac Newton Roel Schroeven -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Op 2005-11-24, Roel Schroeven schreef [EMAIL PROTECTED]: Antoon Pardon wrote: Op 2005-11-24, Mike schreef [EMAIL PROTECTED]: and many a time. I've been annoyed (in Java and MS christelijke vorm er van. frameworks) Antoon, I don't think Mike wrote it like that :) You are right, I don't know what happened, but a piece of text from an other article was pasted in somehow. My apologies to everyone and especially Mike. -- Antoon Pardon -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Giovanni Bajo [EMAIL PROTECTED] wrote in message news:[EMAIL PROTECTED] Mike wrote: How can a (user-defined) class ensure that its instances are immutable, like an int or a tuple, without inheriting from those types? What caveats should be observed in making immutable instances? IMHO, this is usually (but not always) a mistake. (If you're programming a missle guidance system, or it makes your program go faster it's not a mistake :)) So are PRIVATE, CONST (all types), SEALED, FINAL, etc -- even the best programmer doesn't foresee what a user will want to do to make best use of his components, and many a time I've been annoyed (in Java and MS frameworks) by not being able to access/modify/subclass a member/class that I know is there because it has to be there (or because I can see it in the debugger), but it's not accessable because the programmer was overly clever and had been to OOP school. There's a big difference. An immutable object has a totally different semantic, compared to a mutable object. If you document it to be immutable, and maybe even provide __eq__ /__hash__, adding attributes from it is surely an user bug. And surely a bug for which I'd expect an exception to be raised. Why is it surely a bug? It is arguable whether adding new attributes (vs. changing those that are already there) is, in fact, mutation. How will adding user attibutes that your code knows nothing about break the contracts you have specified? If __hash__/__eq__ does not look at the new attributes, all the better - as these attributes are just along for the ride. (But if the hash reflected into all attrs, things would indeed break.) Personally, adding attributes to existing objects would not be my preferred programming style, epsecailly in a langauge like Python with rich and easy-to-use associative data structures, but sometimes it's the quickest or only way to get something done -- if you are unwilling (or more likely, unable) to modify all the levels of method signatures required to pass new information about an object/state along. I can see how a compile-time *warning* would be of value to show it is not the *desired* usage pattern in the eyes of the component programmer, but beyond that, why get in the way? Python is not Java or any other language -- sometimes I don't like the total dynamicity either (I'd like optional types and/or type-inference), but it is what it is. Sometimes, I play with some of my objects and I have to go back and check documentation whether they are immutable or not, to make sure I use the correct usage pattern. That's fine, this is what docs are for, but couldn't Python give me some way to enforce this so that, if I or some other dev do the mistake, it doesn't go unnoticed? It sounds like what you may want are opaque objects where you can control access better -- if that's so, keep them all hidden, and just pass back a handle or proxy - you could always implement restrictred/readonly or copy-on-write semantics. (If there isn't one already, auto-proxy generation for this sort of thing sounds like a fun python cookbook recipe...) -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] [EMAIL PROTECTED] writes: Mike Meyer wrote: Giovanni Bajo [EMAIL PROTECTED] writes: Mike Meyer wrote: Note that this property of __slots__ is an implementation detail. You can't rely on it working in the future. I don't rely on it. I just want to catch bugs in my code. I certainly hope you're not relying on it to catch bugs. You should do proper testing instead. Not only will that catch pretty much all the bugs you mention later - thus resolving you of the need to handcuff clients of your class - it will catch lots of other bugs as well. That is an ideal case and we all know the real world is not ideal or every program would be bug free. And I don't think anyone would solely relies on the language feature for spotting bugs. Whether this kind of guard is useful is another story. Python generally regards languages features that either require extra typing or reduce the flexibility of the language for the purpose of catching bugs as not useful. Some people disagree with this, but it's the way Python is. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Antoon Pardon [EMAIL PROTECTED] wrote in message news:[EMAIL PROTECTED] Op 2005-11-24, Mike schreef [EMAIL PROTECTED]: [...snip...] ...but I think Python's voluntary DoThis, _DoThisIfYouReallyHaveTo, and __You'dBetterKnowWhatYou'reDoing__ approach is a better way to go than the undefeatable keyword approach. I disagree. Suppose I have the following code. from module import __take_care__ __private_detail__ = ... I now have two variable that are flaged the same way, but they are not. __take_care__ is a private variable from an other module which I should use with extreme care not to break the other package. __private_detail__ on the other hand is just keeping private data for my own module, which I should care about as just any other variable in my module. It are other modules that should take special care if they should choose to import this variable. If you just import the module and use __private_detail__ vs. module.__take_care__ -- that solves that problem :) That is why I don't think the underscore prefixes are very usefull. They constantly flag to take care with a specific variable, while that variable is nothing special within the module itself. I didn't say that the methods used were perfect or fully expressive, but just in the right direction. Maybe there should be a few more variations, and they should be documented and blessed, and *tools* can honor them as they see fit. (Different syntax hilighting, lint checking, etc.) m -- Antoon Pardon -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney [EMAIL PROTECTED] writes: I'm looking for a consenting adults restriction: classes will have immutable instances only where it makes sense from the class protocol. I'm not going to lose sleep over users who go looking for trouble. I think you're defining immutable differently than I do. Python already supports attributes that clients can't rebind. You can make an instance in which all attributes have that property. However attributes added by a client aren't really yours. They don't change the immutability of your attributes, or affect the behavior of your class in any way. Such attributes don't really belong to your class; they belong to the client. Even in full BD languages, it's trivial to overcome this restriction with a subclass: i = int() i 0 i.foo = 1 Traceback (most recent call last): File stdin, line 1, in ? AttributeError: 'int' object has no attribute 'foo' class Aint(int): pass ... m = Aint() m 0 m.foo = 1 m.foo 1 The extra class is the kind of boilerplate that Python in general has so little of, and BD languages so much of. In Python, I can even fix it so *your* code uses my wrapped version: import Finney class Addable(Finnney.Immutable): pass Finney.Immutable = Addable Which means that from now on *your* code that tries to create Immutables will actually get Addables. The inability to do this in BD languages is - well, painfull. That Python doesns't require the boilerplate in a good thing. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] wrote in message news:[EMAIL PROTECTED] Mike Meyer wrote: Giovanni Bajo [EMAIL PROTECTED] writes: Mike Meyer wrote: Note that this property of __slots__ is an implementation detail. You can't rely on it working in the future. I don't rely on it. I just want to catch bugs in my code. I certainly hope you're not relying on it to catch bugs. You should do proper testing instead. Not only will that catch pretty much all the bugs you mention later - thus resolving you of the need to handcuff clients of your class - it will catch lots of other bugs as well. That is an ideal case and we all know the real world is not ideal or every program would be bug free. And I don't think anyone would solely relies on the language feature for spotting bugs. Whether this kind of guard is useful is another story. This is a case where the *language* should be expressive as possible, and the *tools* surrounding it should be of more help. Have I ever mistyped a python variable and introduced a bug? -- many times, and it's really annoying. It's a fault that there's no tool that realizes that positon looks a hell of a lot like position, more than it's the compiler's fault to make such an assumption, because the compiler can't close the loop with the user, but the tool can. (Or my fault for not using such a tool - I know there's pylint, etc.) -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney [EMAIL PROTECTED] wrote: ... A type implemented in C offers different possibilities than one implemented in Python -- no deep conceptual reason, just practical ones. So, in the hypothetical situation that all Python types were implemented in pure Python, what would the ideal behaviour for immutables be? Or would there be no immutables? Pypy is implementing Python in Python and using just the same semantics as CPython. Of course, there IS some sleight of hand, because there are still two sides -- interpreter level and application level... stuff implemented in interpreter level Python plays just the same role as stuff implemented in C does in CPython. Musing theoretically, I can see an *ideal* approach would have to meet higher aesthetic goals than Python's -- reach for richer symmetry, e.g., all types existing in mutable and immutable flavors (Ruby comes sort of close, with plain and frozen objects). Python's more about pragmaticity than purity (and, therefore, than idealness)... I'm looking for a consenting adults restriction: classes will have immutable instances only where it makes sense from the class protocol. I'm not going to lose sleep over users who go looking for trouble. Yep, I understand this, now that you've explained in more detail, and FWIW I do approve. One more piece of advice: you might document that, in circumstances where (using a normal Python class's instances) the obvious approach would be to add some per-instance attribute to the instances (with semantics totally outside the class), your users might be better advised to employ a weakref.WeakKeyDictionary with the instances as keys. Although a tad more cumbersome, they can get the same semantics this way, even though it may seem inside-out wrt the intuitive approach. Alex -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: Note that this property of __slots__ is an implementation detail. You can't rely on it working in the future. I don't rely on it. I just want to catch bugs in my code. I certainly hope you're not relying on it to catch bugs. You should do proper testing instead. Not only will that catch pretty much all the bugs you mention later - thus resolving you of the need to handcuff clients of your class - it will catch lots of other bugs as well. This sounds a little academic. Writing a real Python program without testing is impossible or close to it, so you are really not telling me anything new. Even *with* testing, there are bugs. I'm sure you well know this. My feeling is that you're trying to get too much out of my words. I'm not trying to handcuff anyone. You seem to concentrate on me trying to avoid people adding attributes to my precious objects. It's not that. If I write a class and want it to be immutable, it is because it has to be so. If I write a queue class and I say that people shouldn't call pop() if it's empty, I mean it. If I enforce it with a RuntimeError, I'm not thinking I'm handcuffing someone. I don't see a ImmutableError to be so different from it. I often design objects that I want to be immutable. I might keep it as a key in dictionaries, or I might have external, non-intrusive caches of some kind relying on the fact that the instance does not change. Of course, it *might* be that testing uncovers the problem. Unittests tend to be pretty specific, so in my experience they happen to miss *new* bugs created or uncovered by the integration of components. Or if they hit it, you still have to go through debug sessions. An ImmutableError would spot the error early. In my view, enforcing immutability is no different from other forms of self-checks. Do you reckon all kind of asserts are useless then? Surely they don't help for anything that a good unittest couldn't uncover. But they help catching bugs such as breakage of invariants immediately as they happen. Immutability can be such an invariant. If it's not a wart, why would it be a wart for user-defined types to have the same behaviour? It's a wart because user-defined classes *don't* have the same behavior. Then *my* solution for this would be to give user-defined classes a way to behave like builtins, eg. explicitally and fully implement immutability. Well, if you want to propose a change to the language, you need a good use case to demonstrate the benefits of such a change. Do you have such a use case? Catching bugs doesn't qualify, otherwise Python would be radically different from what it is. One good reason, in my opinion, is that there *are* immutable objects in Python, among builtins. And people can easily build extension objects which are immutable. So being impossible to write a regular object in Python which is immutable is not orthogonal to me. Now let me ask you a question. What is a good use case for assert that justifies its introduction in the language? What is a good usecase for module 'unittest' which justifies its introduction in the standard library? Why do you think tuples are immutable and *enforced* to be so? Immutability is an important concept in Python programs, and I'm impressed it does not have explicit support. I'm not convinced that immutability is that important a concept. Yeah, you have to know about it, but it seems more like an implementation detail than a crucial concept. Probably it's just a matter of design styles. I'm not sure it's more important than things like interned strings and the sharing of small integers. Most of the discussion of immutables here seems to be caused by newcomers wanting to copy an idiom from another language which doesn't have immutable variables. Their real problem is usually with binding, not immutability. I'm not such a newcomer, but (how funny) Python is *the* language that introduced me to the concept of immutable objects and their importance in design :) -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Giovanni Bajo [EMAIL PROTECTED] writes: My feeling is that you're trying to get too much out of my words. I'm not trying to handcuff anyone. You seem to concentrate on me trying to avoid people adding attributes to my precious objects. It's not that. If I write a class and want it to be immutable, it is because it has to be so. If I write a queue class and I say that people shouldn't call pop() if it's empty, I mean it. If I enforce it with a RuntimeError, I'm not thinking I'm handcuffing someone. I don't see a ImmutableError to be so different from it. But why would you call it that, when the object isn't actually implemented as immutable? It's pretty misleading to call an object immutable rather than saying that it shouldn't be changed for some reason. Throw an exception that describes why it doesn't make sense to change that particular object instead. As I said before, I think you're confusing the (in Python pretty non-existent) concept of encapsulation with Python's immutable types, which are immutable because the implementation demands it. (A fact I hope will disappear at some point.) -- Björn Lindström [EMAIL PROTECTED] Student of computational linguistics, Uppsala University, Sweden -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
[EMAIL PROTECTED] (Björn Lindström) writes: As I said before, I think you're confusing the (in Python pretty non-existent) concept of encapsulation with Python's immutable types, which are immutable because the implementation demands it. (A fact I hope will disappear at some point.) What implementation demand? If Python's designers wanted mutable strings or tuples, Python could have them. Python strings and tuples are immutable by design, not by accident of implementation. Wanting to make immutable class instances out of the same design considerations is perfectly reasonable. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Björn Lindström wrote: My feeling is that you're trying to get too much out of my words. I'm not trying to handcuff anyone. You seem to concentrate on me trying to avoid people adding attributes to my precious objects. It's not that. If I write a class and want it to be immutable, it is because it has to be so. If I write a queue class and I say that people shouldn't call pop() if it's empty, I mean it. If I enforce it with a RuntimeError, I'm not thinking I'm handcuffing someone. I don't see a ImmutableError to be so different from it. But why would you call it that, when the object isn't actually implemented as immutable? I think you misunderstood my message. I'm saying that an ImmutableError wouldn't be a much different form of self-checking compared to the usual TypeError/ValueError/RuntimeError you get when you pass wrong values/types to methods/functions, or you violate invariants of objects. This has nothing to do with dynamism, duck typing, dynamic binding and whatnot. Some objects have deep invariants which can't be broken. Why do you think we have a frozenset, for instance? By Mike's argument, we shouldn't have it. And we should be able to use a regular mutable set as dictionary key. Unittests will catch errors. Instead, we got two classes instead of one, immutability is *enforced*, and sets can't be used as dictionary keys. This is all good in my opinion, and follows the good rule of catch errors early. Throw an exception that describes why it doesn't make sense to change that particular object instead. *How* can I do? There is no language construct which lets me specifies an exception to throw whenever someone modifies my object. *Even* if I got partial support for immutable types (like __new__ which can be used to initialize immutable objects). As I said before, I think you're confusing the (in Python pretty non-existent) concept of encapsulation with Python's immutable types, which are immutable because the implementation demands it. (A fact I hope will disappear at some point.) You seriously believe that strings, integers and tuples are immutable because of implementation details? I believe they are part of a language design -- and a good part of it. -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike wrote: There's a big difference. An immutable object has a totally different semantic, compared to a mutable object. If you document it to be immutable, and maybe even provide __eq__ /__hash__, adding attributes from it is surely an user bug. And surely a bug for which I'd expect an exception to be raised. Why is it surely a bug? It is arguable whether adding new attributes (vs. changing those that are already there) is, in fact, mutation. If we agree that *changing* attributes is a bug for those classes, we're already a step beyond in this discussion :) About adding attributes, I agree that it's kind of a grey area. Per-se, there is nothing wrong. My experience is that they give the user a false expectation that the object can be modified. It ends up with an object with attributes which can't be modified because that'd break invariants, and others which are freely modificable. In fact, the only thing that you are adding an attribute to *that* instance, and not to all the *equivalent* instances (by definition of __hash__/__eq__) is questionable and bug-prone. You might end up *thinking* you have that very instance around, while you don't. In fact, with immutable objects, you are not supposed to think in terms of instances, but rather of values. When I see a string like foobar I don't care if it's the same instance of a foobar I saw before. If I could add an attribute to foobar, I might end up believing that whenever I see a foobar around, it will have that attribute. As you said, Python has rich data structures which lets you still find good ways to carry around additional information. So why trying so hard to get into trouble? It sounds like what you may want are opaque objects where you can control access better No that's a different issue. One example of my immutable classes is Point2D (two attributes: x/y). Having it immutable gives it many useful properties, such as a real value semantic. -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Giovanni Bajo [EMAIL PROTECTED] writes: Mike Meyer wrote: Note that this property of __slots__ is an implementation detail. You can't rely on it working in the future. I don't rely on it. I just want to catch bugs in my code. I certainly hope you're not relying on it to catch bugs. You should do proper testing instead. Not only will that catch pretty much all the bugs you mention later - thus resolving you of the need to handcuff clients of your class - it will catch lots of other bugs as well. My feeling is that you're trying to get too much out of my words. I'm not trying to handcuff anyone. You seem to concentrate on me trying to avoid people adding attributes to my precious objects. Because *that's* the use case that you're preventing that I have problems with. It's not that. If I write a class and want it to be immutable, it is because it has to be so. If I write a queue class and I say that people shouldn't call pop() if it's empty, I mean it. If I enforce it with a RuntimeError, I'm not thinking I'm handcuffing someone. I don't see a ImmutableError to be so different from it. And I have no problems with that. If you believe your class should throw an error if someone calls an instances pop() method when it's empty, do so. Likewise, if you want to make it so a client can't change your attributes, feel free to do so. However, when you prevent a client from adding an attribute, you're not merely making your objects immutable, you're making them static. Python isn't a static language, it's a dynamic language. I consider parts of it that are static to be warts. In my view, enforcing immutability is no different from other forms of self-checks. Do you reckon all kind of asserts are useless then? Surely they don't help for anything that a good unittest couldn't uncover. But they help catching bugs such as breakage of invariants immediately as they happen. Immutability can be such an invariant. Adding an attribute can't break an invariant. The only way an attribute can affect an invariant is if the invariant references it. If it references it it, then it must exist - so I can't add it. If it's not a wart, why would it be a wart for user-defined types to have the same behaviour? It's a wart because user-defined classes *don't* have the same behavior. Then *my* solution for this would be to give user-defined classes a way to behave like builtins, eg. explicitally and fully implement immutability. Well, if you want to propose a change to the language, you need a good use case to demonstrate the benefits of such a change. Do you have such a use case? Catching bugs doesn't qualify, otherwise Python would be radically different from what it is. One good reason, in my opinion, is that there *are* immutable objects in Python, among builtins. And people can easily build extension objects which are immutable. So being impossible to write a regular object in Python which is immutable is not orthogonal to me. I didn't ask for a reason, I asked for a use case. Orthogonality is a good thing, but so is generality. So I'll argue that the correct way to make this situation orthogonal is to make builtin objects more general by making it possible to add attributes to all of them. On the other hand, practicality beats purity, and doing the above has a significant cost in the current implementation, so leave it like it is. Now let me ask you a question. What is a good use case for assert that justifies its introduction in the language? What is a good usecase for module 'unittest' which justifies its introduction in the standard library? Unittesting doesn't change the language, and is part of any good development methodology. Assert is a shorthand for if ... ; raise that vanishes when you turn on optimization. It's cleaner and more clearly expresses the intent of the programmer, and saves a fair amount of boilerplate in the best case. Why do you think tuples are immutable and *enforced* to be so? That you can't add attributes to a tuple is a detail of the implementation; it's true for non-immutable types as well. I'm not sure it's more important than things like interned strings and the sharing of small integers. Most of the discussion of immutables here seems to be caused by newcomers wanting to copy an idiom from another language which doesn't have immutable variables. Their real problem is usually with binding, not immutability. I'm not such a newcomer, but (how funny) Python is *the* language that introduced me to the concept of immutable objects and their importance in design :) Well, that would explain why you think it's so important - it's where you first encountered it. I'd argue that it's no more important than identity - which is what I was searching for when I talked about interned strings sharing small integers. There are builtin types that preserve identity for equal instances, at least under some conditions. There are no constructs
Re: Making immutable instances
Giovanni Bajo [EMAIL PROTECTED] writes: Björn Lindström wrote: Why do you think we have a frozenset, for instance? By Mike's argument, we shouldn't have it. Not *my* arguments, certainly. Not unless you're seriously misinterpreting them. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Giovanni Bajo [EMAIL PROTECTED] wrote: ... As I said before, I think you're confusing the (in Python pretty non-existent) concept of encapsulation with Python's immutable types, which are immutable because the implementation demands it. (A fact I hope will disappear at some point.) You seriously believe that strings, integers and tuples are immutable because of implementation details? I believe they are part of a language design -- and a good part of it. Definitely. When I first designed gmpy, I wanted to make its number types mutable, thinking this might probably enhance performance, but I double checked with Python cognoscenti first -- and the result was a plebiscite for IMmutable numbers (at the time, I was sort of new at Python, and didn't really get it, but now I do;-). Alex -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: And I have no problems with that. If you believe your class should throw an error if someone calls an instances pop() method when it's empty, do so. Likewise, if you want to make it so a client can't change your attributes, feel free to do so. However, when you prevent a client from adding an attribute, you're not merely making your objects immutable, you're making them static. Python isn't a static language, it's a dynamic language. I consider parts of it that are static to be warts. I always thought that adding an attribute was just as bad as changing the attributes, for an immutable object. But I now see your point (eventually!), they are pretty different issues. But, whatever attribute you add to the instance, it should *also* be immutable (so that, in other words, wouldn't be so different than carrying around a tuple with the original instance and the added attribute). This said, I think I devise that a language support for enforcing immutability could allow adding attributes to instance -- as long as those attributes then become immutable as well. I'm not sure it's more important than things like interned strings and the sharing of small integers. Most of the discussion of immutables here seems to be caused by newcomers wanting to copy an idiom from another language which doesn't have immutable variables. Their real problem is usually with binding, not immutability. I'm not such a newcomer, but (how funny) Python is *the* language that introduced me to the concept of immutable objects and their importance in design :) Well, that would explain why you think it's so important - it's where you first encountered it. Yes. But I'm familiar with different object semantics, and I found the immutable objects to be a pretty good replacement of value semantics, and to implement a kind-of pass-by-value convention in a language which only has references. I'd argue that it's no more important than identity - which is what I was searching for when I talked about interned strings sharing small integers. There are builtin types that preserve identity for equal instances, at least under some conditions. There are no constructs for helping you do that with user-defined objects. Should we add them for the sake of orthogonality? I don't think so - not without a good use case. I don't think identity is important for immutable objects (as I wrote elsewhere), so I don't think adding language constucts for this would prove useful. Instead, immutable objects *are* common, and we still miss a way to mark them as such. -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Giovanni Bajo [EMAIL PROTECTED] writes: However, when you prevent a client from adding an attribute, you're not merely making your objects immutable, you're making them static. No I don't believe that. If an object is immutable, then obj.serialize() should return the same string every time. If you can add attributes then the serialization output will become different. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Paul Rubin wrote: Giovanni Bajo [EMAIL PROTECTED] writes: [pay attention to the quoting, I didn't write that :) ] Mike Meyer wrote: However, when you prevent a client from adding an attribute, you're not merely making your objects immutable, you're making them static. No I don't believe that. If an object is immutable, then obj.serialize() should return the same string every time. If you can add attributes then the serialization output will become different. I guess it might be argued that the method serialize() could return whatever value it returned before, and that the added attribute could be optional (eg. think of it as a cache that can be recomputed from the immutable attributes at any time). It's kind of a grey area. Surely, I would *not* mind if language support for immutability prohibited this :) -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: Björn Lindström wrote: Why do you think we have a frozenset, for instance? By Mike's argument, we shouldn't have it. Not *my* arguments, certainly. Not unless you're seriously misinterpreting them. Sorry then, I probably am. There must be a misunderstanding somewhere. What is your position about frozenset? By my understanding of your arguments, it is a hand-cuffed version of set, which just prevents bugs that could still be caught by testing. The same applies for the arbitrary restriction of not allowing sets to be key dictionaries (with their hash value being their id). -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Giovanni Bajo [EMAIL PROTECTED] writes: Mike Meyer wrote: And I have no problems with that. If you believe your class should throw an error if someone calls an instances pop() method when it's empty, do so. Likewise, if you want to make it so a client can't change your attributes, feel free to do so. However, when you prevent a client from adding an attribute, you're not merely making your objects immutable, you're making them static. Python isn't a static language, it's a dynamic language. I consider parts of it that are static to be warts. I always thought that adding an attribute was just as bad as changing the attributes, for an immutable object. But I now see your point (eventually!), they are pretty different issues. But, whatever attribute you add to the instance, it should *also* be immutable (so that, in other words, wouldn't be so different than carrying around a tuple with the original instance and the added attribute). This said, I think I devise that a language support for enforcing immutability could allow adding attributes to instance -- as long as those attributes then become immutable as well. That's cool, but only because immutability is such a slippery concept in Python. We both agree that tuplee are immutable, right? So consider this: x = f() type(x) type 'tuple' id(x) 136810980 y = copy.deepcopy(x) y is x False y == x True f2(x) id(x) 136810980 y == x False So I'm perfectly willing to let your class declare that my attributes be immutable, just so long as you mean the same thing by that as you mean when you refer to tuples as immutable. I'm not sure it's more important than things like interned strings and the sharing of small integers. Most of the discussion of immutables here seems to be caused by newcomers wanting to copy an idiom from another language which doesn't have immutable variables. Their real problem is usually with binding, not immutability. I'm not such a newcomer, but (how funny) Python is *the* language that introduced me to the concept of immutable objects and their importance in design :) Well, that would explain why you think it's so important - it's where you first encountered it. Yes. But I'm familiar with different object semantics, and I found the immutable objects to be a pretty good replacement of value semantics, and to implement a kind-of pass-by-value convention in a language which only has references. Like I said, I don't have a problem with immutable objects per se. It's taking away my ability to extend the objects in all the ways that Python allows that bothers me. Personally, I haven't found much use for immutable *objects*, as for immutable *attributes*. Python allows the latter. In Python, you create an immutable object by creating an object with no mutable attributes. I'd argue that it's no more important than identity - which is what I was searching for when I talked about interned strings sharing small integers. There are builtin types that preserve identity for equal instances, at least under some conditions. There are no constructs for helping you do that with user-defined objects. Should we add them for the sake of orthogonality? I don't think so - not without a good use case. I don't think identity is important for immutable objects (as I wrote elsewhere), so I don't think adding language constucts for this would prove useful. Instead, immutable objects *are* common, and we still miss a way to mark them as such. I think identity is important from an implementation point of view. Implementation is important - so having constructs that let you deal with this is useful. Python has those constructs. What Python doesn't have in general is the ability to mark objects. You have the ability to create attributes that are immutable. You can create immutable objects by creating objects which have no mutable attributes. What more do you need? mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Paul Rubin http://[EMAIL PROTECTED] writes: Giovanni Bajo [EMAIL PROTECTED] writes: However, when you prevent a client from adding an attribute, you're not merely making your objects immutable, you're making them static. No I don't believe that. If an object is immutable, then obj.serialize() should return the same string every time. If you can add attributes then the serialization output will become different. There isn't a standard serialize method in Python, so I don't know how you want to define it. I can think of perfectly reasonable definitions of serialize where obj.serialize() won't always return the same string on an immutable object, even if you don't allow adding attributes. Personally, I'd argue that serialize shouldn't return the extra attribute. If you want to add an attribute that gets serialized, you need to subclass the immutable class, add the attribute there, and extend serialize to include it. Whether or not that's reasonable depends on how you want to define serialize. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Giovanni Bajo [EMAIL PROTECTED] writes: Mike Meyer wrote: Björn Lindström wrote: Why do you think we have a frozenset, for instance? By Mike's argument, we shouldn't have it. Not *my* arguments, certainly. Not unless you're seriously misinterpreting them. Sorry then, I probably am. There must be a misunderstanding somewhere. I'm seeing posts from you attribute to Mike Meyer (me) and Mike - some of which definitely weren't me. So maybe it wasn't mine. What is your position about frozenset? By my understanding of your arguments, it is a hand-cuffed version of set, which just prevents bugs that could still be caught by testing. I have exactly the same problem with frozensets as I do with sets - I can't add attributes to either one. That frozenset can't be changed doesn't bother me particularly. The same applies for the arbitrary restriction of not allowing sets to be key dictionaries (with their hash value being their id). I can't parse that. What do you mean by key dictionaries? mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney wrote: How can a (user-defined) class ensure that its instances are immutable, like an int or a tuple, without inheriting from those types? What caveats should be observed in making immutable instances? In short, you can't. I usually try harder to derive from tuple to achieve this (defining a few read-only properties to access item through attributes). Using __slots__ is then required to avoid people adding attributes to the instance. In fact, I don't know the rationale. I would think it would be a great addition to be able to say __immutable__ = True or something like that. Or at least, I'd be grateful if someone explained me why this can't or shouldn't be done. -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Giovanni Bajo [EMAIL PROTECTED] writes: Ben Finney wrote: How can a (user-defined) class ensure that its instances are immutable, like an int or a tuple, without inheriting from those types? What caveats should be observed in making immutable instances? In short, you can't. I usually try harder to derive from tuple to achieve this (defining a few read-only properties to access item through attributes). Using __slots__ is then required to avoid people adding attributes to the instance. Note that this property of __slots__ is an implementation detail. You can't rely on it working in the future. I'm curious as to why you care if people add attributes to your immutable class. Personally, I consider that instances of types don't let me add attributes to be a wart. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer [EMAIL PROTECTED] wrote: Giovanni Bajo [EMAIL PROTECTED] writes: In short, you can't. I usually try harder to derive from tuple to achieve this (defining a few read-only properties to access item through attributes). Using __slots__ is then required to avoid people adding attributes to the instance. Note that this property of __slots__ is an implementation detail. You can't rely on it working in the future. That's one thing I meant when I asked about caveats: implementation warnings. Thanks. Are there other, more dependable, ways of making immutable objects? I'm curious as to why you care if people add attributes to your immutable class. Personally, I consider that instances of types don't let me add attributes to be a wart. And this is another meaning: style caveats. I genuinely want to understand these issues. I refer you to a similar question: do you consider it a wart that you can't add attributes to instances of Python's built-in types? foo = (spam, eggs) foo.comment = I love it. Traceback (most recent call last): File stdin, line 1, in ? AttributeError: 'tuple' object has no attribute 'comment' bar = 1 bar.base = 10 Traceback (most recent call last): File stdin, line 1, in ? AttributeError: 'int' object has no attribute 'base' Is this a wart? Why? If it's not a wart, why would it be a wart for user-defined types to have the same behaviour? -- \ I spilled spot remover on my dog. Now he's gone. -- Steven | `\Wright | _o__) | Ben Finney -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer [EMAIL PROTECTED] writes: I'm curious as to why you care if people add attributes to your immutable class. Personally, I consider that instances of types don't let me add attributes to be a wart. I agree. To me it seems like the OP kind of wants to implement encapsulation from the back way. Anyway, as he doesn't mention anything about using this immutability for any kind of optimisation, I assume it's about Control. -- Björn Lindström [EMAIL PROTECTED] Student of computational linguistics, Uppsala University, Sweden -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney [EMAIL PROTECTED] writes: Are there other, more dependable, ways of making immutable objects? Your answer can be found at URL: http://www.cs.bgu.ac.il/~omri/Humor/write_in_c.html I'm curious as to why you care if people add attributes to your immutable class. Personally, I consider that instances of types don't let me add attributes to be a wart. I refer you to a similar question: do you consider it a wart that you can't add attributes to instances of Python's built-in types? Didn't I just say that I thought it was a wart? Is this a wart? Why? Because it means I have to wrap them to if I want a typefoo with an extra attribute. I don't have to do that for classes. It makes builtin types different from user-defined classes in ways other than performance, which is a bad thing. If it's not a wart, why would it be a wart for user-defined types to have the same behaviour? It's a wart because user-defined classes *don't* have the same behavior. mike -- Mike Meyer [EMAIL PROTECTED] http://www.mired.org/home/mwm/ Independent WWW/Perforce/FreeBSD/Unix consultant, email for more information. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney [EMAIL PROTECTED] wrote: How can a (user-defined) class ensure that its instances are immutable, like an int or a tuple, without inheriting from those types? You can make a good start by defining __setattr__, __delattr__ (and __setitem__ and __delitem__ if your class is a container) to raise exceptions. Of course, these restrictions can be easily worked around by a sufficiently determined attacker... but if you have to think of the user of your code as an attacker, you've got worse problems than this trifling one. Do not define any of the in-place operator special methods, such as __iadd__ and friends (or, if you're inheriting from a class that does define them, override them to raise exceptions). What caveats should be observed in making immutable instances? Remember that your redefined __setattr__ IS in place even when you're initializing your istance, so remember to delegate attribute setting to the superclass (the other special methods mentioned above are less likely to byte you). You will probably want to define __hash__ and __eq__ if you're going to the trouble of making instances immutable. Alex -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Alex Martelli [EMAIL PROTECTED] wrote: Ben Finney [EMAIL PROTECTED] wrote: How can a (user-defined) class ensure that its instances are immutable, like an int or a tuple, without inheriting from those types? You can make a good start by defining __setattr__, __delattr__ (and __setitem__ and __delitem__ if your class is a container) to raise exceptions. [...] Do not define any of the in-place operator special methods, such as __iadd__ and friends (or, if you're inheriting from a class that does define them, override them to raise exceptions). That sounds more Pythonic than hacking __slots__. Thanks. Remember that your redefined __setattr__ IS in place even when you're initializing your istance, so remember to delegate attribute setting to the superclass (the other special methods mentioned above are less likely to byte you). So, for a class that needs to set attributes in __init__ (but after that, become immutable), how do I get around this? Should I make a _FooFunctionality class, and then inherit from that to make Foo as the immutable class that actually gets exported? You will probably want to define __hash__ and __eq__ if you're going to the trouble of making instances immutable. Good tip, thanks. -- \ I'm having amnesia and d?j? vu at the same time. I feel like | `\ I've forgotten this before sometime. -- Steven Wright | _o__) | Ben Finney -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Alex Martelli [EMAIL PROTECTED] wrote: Ben Finney [EMAIL PROTECTED] wrote: How can a (user-defined) class ensure that its instances are immutable, like an int or a tuple, without inheriting from those types? [...] Of course, these restrictions can be easily worked around by a sufficiently determined attacker... but if you have to think of the user of your code as an attacker, you've got worse problems than this trifling one. I've probably stumbled across something that people often want to do for ill-considered reasons; I don't really understand the reaction I'm getting. Why is I want to make objects immutable seen as I don't trust my users? Are Python's existing immutable types also seen the same way? If not, why the distinction? For context, I'm intending for the immutability of class instances to be a properly documented part of the class protocol. Does that sound more reasonable? -- \ In general my children refuse to eat anything that hasn't | `\ danced on television. -- Erma Bombeck | _o__) | Ben Finney -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney [EMAIL PROTECTED] wrote: ... Remember that your redefined __setattr__ IS in place even when you're initializing your istance, so remember to delegate attribute setting to the superclass (the other special methods mentioned above are less likely to byte you). So, for a class that needs to set attributes in __init__ (but after that, become immutable), how do I get around this? Should I make a As I said, you delegate attribute setting to the superclass. E.g: class Immut(object): ... def __setattr__(*a): raise TypeError, 'immutable' ... def __init__(self, v=23): ... super(Immut,self).__setattr__('v', v) ... x=Immut() x.v 23 x.v=42 Traceback (most recent call last): File stdin, line 1, in ? File stdin, line 2, in __setattr__ TypeError: immutable Alex -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney [EMAIL PROTECTED] wrote: ... Of course, these restrictions can be easily worked around by a sufficiently determined attacker... but if you have to think of the user of your code as an attacker, you've got worse problems than this trifling one. I've probably stumbled across something that people often want to do for ill-considered reasons; I don't really understand the reaction I'm getting. Why is I want to make objects immutable seen as I don't trust my users? Are Python's existing immutable types also seen the same way? If not, why the distinction? A type implemented in C offers different possibilities than one implemented in Python -- no deep conceptual reason, just practical ones. A substantial fraction of the time, people asking how do I stop the users of my code from doing X proceed by screaming but they could still do X if they hopped on their left foot in a moonless midnight while sprinkling bat's blood! as a response to any suggestion. So, when you ask how do I stop the users of my code from doing X without qualification, you're quite likely to get such disclaimers. If you don't want them, learn to ask about stopping your users from ACCIDENTALLY doing X, and no reasonable respondant will fail to notice the qualification. For context, I'm intending for the immutability of class instances to be a properly documented part of the class protocol. Does that sound more reasonable? There was nothing unreasonable in your original request, either; and I don't think that making it explicit that you intended to document the restriction would have changed my answer (although an explicit acknowlegment that you're looking for restrictions against accidental misuse rather than against determined attackers surely would). Alex -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Alex Martelli wrote: A substantial fraction of the time, people asking how do I stop the users of my code from doing X proceed by screaming but they could still do X if they hopped on their left foot in a moonless midnight while sprinkling bat's blood! as a response to any suggestion. So, when you ask how do I stop the users of my code from doing X without qualification, you're quite likely to get such disclaimers. If you don't want them, learn to ask about stopping your users from ACCIDENTALLY doing X, and no reasonable respondant will fail to notice the qualification. Interestingly, that is what I read from the OP, even without the ACCIDENTALLY. -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Ben Finney [EMAIL PROTECTED] wrote in message news:[EMAIL PROTECTED] Howdy all, How can a (user-defined) class ensure that its instances are immutable, like an int or a tuple, without inheriting from those types? What caveats should be observed in making immutable instances? IMHO, this is usually (but not always) a mistake. (If you're programming a missle guidance system, or it makes your program go faster it's not a mistake :)) So are PRIVATE, CONST (all types), SEALED, FINAL, etc -- even the best programmer doesn't foresee what a user will want to do to make best use of his components, and many a time I've been annoyed (in Java and MS frameworks) by not being able to access/modify/subclass a member/class that I know is there because it has to be there (or because I can see it in the debugger), but it's not accessable because the programmer was overly clever and had been to OOP school. A fine-grained capability architecture married to the language and runtime where I can declare my own level cleverness to override the programmer's would be nice, but I think Python's voluntary DoThis, _DoThisIfYouReallyHaveTo, and __You'dBetterKnowWhatYou'reDoing__ approach is a better way to go than the undefeatable keyword approach. m -- \ Love is the triumph of imagination over intelligence. -- | `\ Henry L. Mencken | _o__) | Ben Finney -- http://mail.python.org/mailman/listinfo/python-list
Re: Making immutable instances
Mike Meyer wrote: Note that this property of __slots__ is an implementation detail. You can't rely on it working in the future. I don't rely on it. I just want to catch bugs in my code. I'm curious as to why you care if people add attributes to your immutable class. Personally, I consider that instances of types don't let me add attributes to be a wart. To catch stupid bugs, typos and whatnot. If an instance is immutable, you can't modify it, period. If you do it, it's a bug. So why not have the bug raises an exception, rather than go unnoticed? I don't see your point, either. Why would you want to add attributes to an object documented to be immutable? -- Giovanni Bajo -- http://mail.python.org/mailman/listinfo/python-list