On Oct 1, 2019, at 11:53, Richard Musil <firstname.lastname@example.org> wrote:
Virtual subclassing is key to the way ABCs work. It would be nice if it were explained better in the docs, but I suppose usually people don’t need to know the details unless they’re actually getting involved in something like designing new ABCs, so…
Thanks for the concise explanation. I guess my objection was not about the ABC (or how it works), but about the single fact that the function `issubclass` gives the results which are counter intuitive.
But it only gives counterintuitive results when you do something counterintuitive. That’s how all consenting-adults features work:
Yes, we know, that those three calls:
>>> issubclass(list, object)
are correct, i.e. there is nothing wrong with each one individually. It is just that all together are contradicting. And it is not because of the objects (how they are), but because what the function does, and in particular that it does two different things (but pretends it is one).
If you want to be a purist, Python doesn’t do subtyping—or, at best, subtyping is defined as “whatever the subclass hooks say”, which is meaningless because it’s completely unrestricted.
By the same argument, Python doesn’t do attributes, or at best attribution is defined as “whatever the getattribute/etc. hooks say”, which is meaningless because it’s completely unrestricted.
But in practice, Python objects almost always act pretty much like things that have attributes. And in practice, Python objects almost always act pretty much like things that have subtyping relationships. The fact that Python allows you to do otherwise, and that there are occasional practical reasons to do otherwise, doesn’t really change that. (At least not for people trying to read and write Python code; for someone trying to write an automated correctness prover, it radically breaks everything, and for someone trying to work on the design of ABCs, it makes less difference than that but still more than zero.)
If `issubclass` tested the inheritance, and there was a function `collections.abc.islikeabc` doing the other thing, I would not say a word.
Inheritance is nearly always useless to test for. And islikeabc would also be nearly always useless. The only reason either one is worth testing for is to approximate subtyping.
You know that when isinstance(spam, Eggs) is true, you can use spam as an Eggs and it will generally work. That’s what you care about. You don’t care why it’s true, you just care that it’s true. And it’s generally (but not absolutely always, much less provably always) true if at least one of the following is true:
* Eggs is a base class of type(spam)
* Eggs is a structural-testing ABC where type(spam) meets the test
* Eggs is an ABC where someone explicitly called Eggs.register on type(spam)
* Eggs is a class with a complicated instance hook that does something very unusual but appropriate for this special case, and that unusual thing likes spam
And that’s why there’s a single function that returns true if any of those is true. None of those things on its own is useful; all of them are useful as approximations of subtyping; all of them combined are in practice a more useful approximation of subtyping than any of them on its own.
For what concerns "issubscriptable" my only comment is that so far it does not seem there is a consensus about what exactly "subscriptable" means (or should mean) and the regular user (like myself) could probably be even more confused (like I am about `issubclass` right now).
Python already defines the term “subscription” for the syntactic form spam[eggs], and has done so consistently since 1.x. And it’s not a word that has other meanings in the Python community, or in programming in general. Given that, the most obvious meaning of “subscriptable” is “can be used as the left thing in a subscription”. And that’s what Steven is asking for here.
The problem here is not that you’re confused about the meaning of subscriptable, but that it’s a concept that comes up rarely enough that you never even learned it. Which could be an argument that subscriptable isn’t useful. Or that we really need indexable and keyable as well/instead. Or even that Steven is wrong to think that he wants subscriptable, and what he really wants is indexable, so we don’t even have a use case for subscriptable. (I don’t know that these are very compelling arguments, but at least they’re conceivable ones.) But I can’t see an argument that something called Subscriptable could (or should) actually mean indexable rather than subscriptable.