finding abc's

lars van gemerden lars at rational-it.com
Fri Jan 25 15:05:34 EST 2013


On Friday, January 25, 2013 8:04:32 PM UTC+1, Ian wrote:
> On Fri, Jan 25, 2013 at 10:40 AM, lars van gemerden
> 
> <lars at rational-it.com> wrote:
> 
> > Hi all,
> 
> >
> 
> > i was writing a function to determine the common base class of a number classes:
> 
> >
> 
> [...]
> 
> >
> 
> > and ran common_base(int, float), hoping to get numbers.Number.
> 
> >
> 
> > this did not work because abstract base classes are not always in the mro() of classes.
> 
> >
> 
> > My question is: is there a way to obtain the abc's of a class or otherwise a way to make the function above take abc's into account (maybe via a predefined function)?
> 
> 
> 
> 
> 
> If the abstract base class's module has not been imported, it may not
> 
> even be loaded into memory, even though it is technically considered a
> 
> superclass.  Consider this:
> 
> 
> 
> 
> 
> Python 2.7.1 (r271:86832, Nov 27 2010, 18:30:46) [MSC v.1500 32 bit
> 
> (Intel)] on win32
> 
> Type "help", "copyright", "credits" or "license" for more information.
> 
> >>> def common_base(classes):
> 
> ...     common = set()
> 
> ...     for cls in object.__subclasses__():
> 
> ...         if all(issubclass(c, cls) for c in classes):
> 
> ...             common.add(cls)
> 
> ...     return common
> 
> ...
> 
> >>> common_base([int, float])
> 
> set([<class '_abcoll.Hashable'>])
> 
> >>> import numbers
> 
> >>> common_base([int, float])
> 
> set([<class 'numbers.Number'>, <class '_abcoll.Hashable'>])
> 
> 
> 
> 
> 
> If you're okay with that, then the approach above might work.
> 
> 
> 
> 
> 
> >     while len(common) > 1:
> 
> >         cls1 = common.pop()
> 
> >         cls2 = common.pop()
> 
> >         if issubclass(cls1, cls2):
> 
> >             common.add(cls1)
> 
> >         elif issubclass(cls2, cls1):
> 
> >             common.add(cls2)
> 
> 
> 
> There is a flaw with your set reduction code here.  If neither class
> 
> is a subclass of the other, then both will be removed.  There may not
> 
> actually be a single closest common base class, however.  What would
> 
> you expect the function to return in the following situation?
> 
> 
> 
> class A(object): pass
> 
> class B(object): pass
> 
> class C(A, B): pass
> 
> class D(A, B): pass
> 
> 
> 
> print common_base([C, D])

thanks, good catch, and very concise answer. I'll give up on trying to get abc's   and improve my algorithm.



More information about the Python-list mailing list