1
class Liquid(object):
    def foo(self):
        pass

    def bar(self):
        pass

class Water(Liquid):

上記の 2 つのクラスがあるとします。 WaterはLiquidから継承します。Water が親のメソッドの 1 つを継承するのを制限する方法はありますbar()か?

4

5 に答える 5

5

並べ替え。しかし、それをしないでください。

class Liquid(object):
    def foo(self):
        pass

    def bar(self):
        pass

class Water(Liquid):
    def __getattribute__(self, name):
        if name == 'bar':
            raise AttributeError("'Water' object has no attribute 'bar'")

l = Liquid()
l.bar()
w = Water()
w.bar()
于 2012-04-10T08:58:47.960 に答える
2

メソッドをノーオペレーションにオーバーライドすることはできますが、削除することはできません。そうすることは、オブジェクト指向設計の中核となる原則の 1 つに違反することになります。つまり、親から継承するオブジェクトは、親が使用される場所ならどこでも使用できるようにする必要があります。これは、リスコフの置換原理として知られています。

于 2012-04-10T08:57:27.263 に答える
2

他の答えのように、継承されたメソッドの 1 つを壊すことができます。

別の方法は、「オプションの」メソッドをリファクタリングし、それらを持たない基本クラスから継承することです。

class BaseLiquid(object):
    def foo(self):
        pass

class Barised(object):
    def bar(self):
        pass

class Liquid(BaseLiquid, Barised): pass

class Water(BaseLiquid):
    def drip(self):
        pass
于 2012-04-10T09:03:10.840 に答える
0

これはおそらく良い考えではありませんが、いつでもメタクラスを使用してプライベート属性を実装できます。

def private_attrs(name, bases, attrs):
    def get_base_attrs(base):
        result = {}

        for deeper_base in base.mro()[1:]:
            result.update( get_base_attrs(deeper_base) )

        priv = []
        if "__private__" in base.__dict__:
            priv = base.__private__

        for attr in base.__dict__:
            if attr not in priv:
                result.update( {attr: base.__dict__[attr]} )

        return result


    final_attrs = {}
    for base in bases:
        final_attrs.update( get_base_attrs(base) )

    final_attrs.update(attrs)

    return type(name, (), final_attrs)


class Liquid(object):
    __metaclass__ = private_attrs
    __private__ = ['bar']
    def foo(self):
        pass

    def bar(self):
        pass

class Water(Liquid):
    __metaclass__ = private_attrs

print Water.foo
print Water.bar

出力は次のとおりです。

<unbound method Water.foo>
Traceback (most recent call last):
  File "testing-inheritance.py", line 41, in <module>
    print Water.bar
AttributeError: type object 'Water' has no attribute 'bar'

編集:クラスのベースを変更しないため、これは isinstance() を台無しにします。

于 2012-04-10T09:45:25.587 に答える
-1

http://docs.python.org/release/2.5.2/ref/slots.html

スロット属性を使用して、これを行うことができると思います。

getattrメソッドを実装し、bar が呼び出された場合に適切な例外をスローすることが可能になる場合があります。

ただし、これは悪い設計の兆候であるため、実際にはこれを行いたくないことに同意します。

于 2012-04-10T09:33:18.533 に答える