Python inheritance - how to disable a function

前端 未结 7 881
离开以前
离开以前 2020-12-01 04:18

In C++ you can disable a function in parent\'s class by declaring it as private in the child class. How can this be done in Python? I.E. How can I hide parent\'s function fr

相关标签:
7条回答
  • 2020-12-01 04:51

    There really aren't any true "private" attributes or methods in Python. One thing you can do is simply override the method you don't want in the subclass, and raise an exception:

    >>> class Foo( object ):
    ...     def foo( self ):
    ...         print 'FOO!'
    ...         
    >>> class Bar( Foo ):
    ...     def foo( self ):
    ...         raise AttributeError( "'Bar' object has no attribute 'foo'" )
    ...     
    >>> b = Bar()
    >>> b.foo()
    Traceback (most recent call last):
      File "<interactive input>", line 1, in <module>
      File "<interactive input>", line 3, in foo
    AttributeError: 'Bar' object has no attribute 'foo'
    
    0 讨论(0)
  • 2020-12-01 04:53

    That could be even simpler.

    @property
    def private(self):
        raise AttributeError
    
    class A:
        def __init__(self):
            pass
        def hello(self):
            print("Hello World")
    
    class B(A):
        hello = private # that short, really
        def hi(self):
            A.hello(self)
    
    obj = A()
    obj.hello()
    obj = B()
    obj.hi() # works
    obj.hello() # raises AttributeError
    
    0 讨论(0)
  • 2020-12-01 04:58

    This is the cleanest way I know to do it.

    Override the methods and have each of the overridden methods call your disabledmethods() method. Like this:

    class Deck(list):
    ...
    @staticmethod
        def disabledmethods():
            raise Exception('Function Disabled')
        def pop(self): Deck.disabledmethods()
        def sort(self): Deck.disabledmethods()
        def reverse(self): Deck.disabledmethods()
        def __setitem__(self, loc, val): Deck.disabledmethods()
    
    0 讨论(0)
  • 2020-12-01 04:59

    A variation on the answer of kurosch:

    class Foo( object ):
        def foo( self ):
            print 'FOO!'
    
    class Bar( Foo ):
        @property
        def foo( self ):
            raise AttributeError( "'Bar' object has no attribute 'foo'" )
    
    b = Bar()
    b.foo
    

    This raises an AttributeError on the property instead of when the method is called.

    I would have suggested it in a comment but unfortunately do not have the reputation for it yet.

    0 讨论(0)
  • 2020-12-01 05:14
    class X(object):
        def some_function(self):
            do_some_stuff()
    
    class Y(object):
        some_function = None
    

    This may lead to some nasty and hard to find exceptions being thrown though, so you might try this:

    class X(object):
        def some_function(self):
            do_some_stuff()
    
    class Y(object):
        def some_function(self):
            raise NotImplementedError("function some_function not implemented")
    
    0 讨论(0)
  • 2020-12-01 05:14

    Another approach is define an descriptor that errors on access.

        class NotHereDescriptor:
            def __get__(self, obj, type=None):
                raise AttributeError
        
        class Bar:
            foo = NotHereDescriptor()
    

    This is similar in nature to the property approach a few people have used above. However it has the advantage that hasattr(Bar, 'foo') will return False as one would expect if the function really didn't exist. Which further reduces the chance of weird bugs. Although it does still show up in dir(Bar).

    If you are interested in what this is doing and why it works check out the descriptor section of the data model page https://docs.python.org/3/reference/datamodel.html#descriptors and the descriptor how to https://docs.python.org/3/howto/descriptor.html

    0 讨论(0)
提交回复
热议问题