(original) (raw)

It's mostly a historical accident -- for classic classes, type(inst) was always \`instance' while inst.\_\_class\_\_ was the user-defined class object.

For new-style classes, the idea is that you can write a proxy class that successfully masquerades as another class. Because \_\_class\_\_ is an attribute, a proxy class can fake this attribute. But type() would reveal the proxy class.

IIRC \_\_class\_\_ is used by the isinstance() implementation, although the code is complicated and I wouldn't be surprised if isinstance(x, type(x)) was also true for proxy instances. (I haven't looked at the code in a long time and it's not easy to follow, alas.)

C code that checks the type instead of \_\_class\_\_ is probably one reason why proxy classes have never taken off -- there just are too many exceptions, so the experience is never very smooth, and everyone ends up cursing the proxy class.

Maybe this kind of "strong" proxy class is just not a good idea. And maybe then we needn't worry about the distinction between type() and \_\_class\_\_.

On Sat, Oct 17, 2015 at 10:55 PM, Steven D'Aprano <steve@pearwood.info> wrote:
On Sat, Oct 17, 2015 at 03:45:19PM -0600, Eric Snow wrote:
\> In a recent tracker issue about OrderedDict \[1\] we've had some
\> discussion about the use of type(od) as a replacement for
\> od.\_\_class\_\_.
\[...\]
> The more general question of when we use type(obj) vs. obj.\_\_class\_\_
\> applies to both the language and to all the stdlib as I expect
\> consistency there would result in fewer surprises. I realize that
\> there are some places where using obj.\_\_class\_\_ makes more sense (e.g.
\> for some proxy support). There are other places where using type(obj)
\> is the way to go (e.g. special method lookup). However, the
\> difference is muddled enough that usage is inconsistent in the stdlib.
\> For example, C-implemented types use Py\_TYPE() almost exclusively.
\>
\> So, would it make sense to establish some concrete guidelines about
\> when to use type(obj) vs. obj.\_\_class\_\_? If so, what would those be?
\> It may also be helpful to enumerate use cases for "type(obj) is not
\> obj.\_\_class\_\_".

I for one would like to see a definitive explanation for when they are
different, and when you should use one or the other. The only
obvious example I've seen is the RingBuffer from the Python Cookbook:

http://code.activestate.com/recipes/68429-ring-buffer/



\--
Steve
\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_\_
Python-Dev mailing list
Python-Dev@python.org
https://mail.python.org/mailman/listinfo/python-dev
Unsubscribe: https://mail.python.org/mailman/options/python-dev/guido%40python.org



--
--Guido van Rossum (python.org/\~guido)