4 ms·
Why's this worth noting? There's no reason you shouldn't be able to extend a type with methods to support a new interface, no matter what that type's author in
by mquander 17y ago
Why's this worth noting? There's no reason you shouldn't be able to extend a type with methods to support a new interface, no matter what that type's author intended. It's not in any sense "dangerous" to existing APIs, as changing final variables could potentially be. It seems like completely natural behavior.
- KirinDave 17y agoMaybe so, but it's not trivial to do in java. It's noteworthy because it gives clojure a lot more power when dealing with native libraries.
- pohl 17y agoIt's not in any sense "dangerous" to existing APIs If your job is to deliver and maintain such an API, then by allowing subclassing you have a larger contract you have to maintain when you want to make changes to the underlying class: rather than just the public interface, you also need to worry about the protected interface. If your API is new, you may want to shepherd your users (by marking a class as final) to favor composition over inheritance to maximize your ability to evolve the implementation in ways that don't break.
- mquander 17y agoAh, that's true, if extend can see protected members. I didn't realize that was the case. EDIT: I'm not sure if it is the case or not; I can't find definitive documentation and I don't have a REPL available. Anyone know for sure?
- swannodette 17y agoextend does not create any kind of hierarchy, there's no subclassing going on here. if you try to set a final field you'll get an exception as expected. protected members when everything is immutable is pointless. Clojure cleanly separates values and identities.
- jjs 17y agoprotected members when everything is immutable is pointless. Except when used to mark the boundary between a stable public API and an internal API that is free to change between releases.
- swannodette 17y ago@jjs, The contract is functions not members, and Clojure has a way to declare public and private fns, so what's your argument?
- jjs 17y agoThe contract is functions not members, and Clojure has a way to declare public and private fns, so what's your argument? When I release a new major version of Foo Lib, and your program refers to private members, your program will break when I remove or rename them. Immutability won't protect you from that.
- Raphael_Amiard 17y agoExcept if the public api of foo lib is only functions, which is the case for all clojure libs i've worked with. EDIT: Ha, i just stumbled on this old yegge article, which is quite appropriate i think. With clojure APIs you think in verbs, so nouns are not that important http://steve-yegge.blogspot.com/2006/03/execution-in-kingdom-of-nouns.html http://steve-yegge.blogspot.com/2006/03/execution-in-kingdom... EDIT2 : perfect quote : "In the remotest regions, beyond the Functional Kingdoms, lies a fabled realm called Lambda the Ultimate. In this place it is said that there are no nouns at all, only verbs!" here you go ;)
- jjs 17y agoby allowing subclassing you have a larger contract you have to maintain when you want to make changes to the underlying class: rather than just the public interface, you also need to worry about the protected interface. In other words, if you allow subclassing, then you also have to worry about the interface that you have explicitly marked visible to subclasses. Normally a non-problem, by definition. final is useful when sealing a class that inherits from a parent class with a protected interface, but even if "final" is reduced to an annotation (or even a comment), its presence explicitly limits your end of the API contract.
- swannodette 17y agoThere is no subclassing going on. Take the time to actually read the documentation provided by the link.
- jjs 17y agoThe italicized portion at the top of my comment was a quote from the parent comment.