2016-12-17 4 views
0

AとBの2つのクラスを作成したいと考えています.AとBのどちらかを継承することができます。それらに機能を提供します。問題は、どのように私の好みに基づいてAまたはBを継承するようにCに指示するのですか?私が使用したコードの非常に単純化したバージョンであるPython - 継承するクラスを選択する

class A: 

    def __init__(self, x, y): 
     self.x = x 
     self.y = y 

    def first(self): 
     return do_something(1) 

    def second(self): 
     return do_something(2) 

    def third(self): 
     return do_something(3) 

    def start(self): 
     self.first() 
     self.second() 
     self.third() 

class B(A): 

    def __init__(self, x, y, z): 
     super().__init__(x, y) 
     self.z = z 

    def second(self): 
     super().second() 
     do_stuff() 

    def third(self): 
     do_other_stuff() 

は、物事をより明確にするために、私はこのコードを持っていると仮定します。特に、Aは製造システムのシミュレータを表し、Bは主工作機械の挙動を変更した同じ製造システムのシミュレータを表す。

ここで、いくつかの統計を計算するためのコードを追加します。問題は、クラスCは、どうか、私は継承した場合(前のリストのように)、クラスAまたはクラスB(正確に同じコード、などとまったく同じように動作することである

class C(A): 

    def __init__(self, *args): 
     super().__init__(*args) 
     self.stat = 0 

    def second(self): 
     super().second() 
     self.stat += 1 

    def third(self): 
     super().third() 
     self.stat *= 3 

:何それがないと、このようなものです最初の行class C(B):

どうすれば実現できないのですか?実現できない方法を使用していますか?理想的な解決策は、Cを初期化するときにAまたはBを継承するクラスを選択できることです。クラスCに継承するクラスを渡すことができるかもしれません。

私はいくつかの研究を行い、集約の可能性も見つけました(私はbefoを知らなかった再)、しかし私はそれが本当に有用であるとは思わない。最後の注意として、クラスAには20〜30までのメソッドがあるかもしれないことに注意してください。そして、クラスCがクラスCを追加する場合、クラスA(または継承するBに依存します) 。

P.S.私はこれを行うエレガントな、コード重い、 "ピジョン"の方法を探しています。私はあなたがもっと良くできると思うすべてのアドバイスを本当に楽しみにしています。最後に、私はクラスCを完全に変更することができますが、クラスAとクラスBは同じ変更(小さな変更は別として)のままでなければなりません。

+2

なぜあなたは継承によってこれをやっていますか? * composition *を使用して、 'C'を' A'や 'B'のいずれかのラッパーにして、実行時に必要なものを渡すのはなぜですか?実際に達成しようとしていることのあまり抽象的な例はありませんか? – jonrsharpe

+0

私はもっとうまく説明しようとします:私は、2つの工作機械によって溶接される部品を運ぶN個のAGVがある次のイベントシミュレータを作っています。私は基本バージョンA(私が言ったように、20-30の方法を持つことができます)と、工作機械1の動作が異なる修正バージョンBを持っています。私がCにしたいのは、シミュレータ(AまたはBのいずれか)を実行することですが、何らかのイベントが発生したときに統計演算を追加します(つまり、マシンツール1に入ったパーツが時間をカウントし始め、ツール2は時間を計測するのを止め、平均製造時間を得る) –

+0

私はPythonで有能ではないが、純粋にOOPの注釈で:デコレータパターンを考慮したか? https://en.m.wikipedia.org/wiki/Decorator_pattern – korolar

答えて

1

新しいスタイルクラスとそのメソッドの解決順序を使用できます。

class A(object): 
    def __init__(self, x): 
     pass 

    def foo(self): 
     print "A" 

class B(object): 
    def __init__(self, x, y): 
     pass 

    def foo(self): 
     print "B" 

あなたがAまたはBに機能を追加することを目的とミックスイン構築することができます:

class Cmix(object): 
    def foo(self): 
     super(Cmix, self).foo() 
     print "mix" 

をして(それぞれ、またはBCmixAの両方から継承するこれらの定義を考慮すると

class CA(Cmix, A): 
    pass 

class CB(Cmix, B): 
    pass 
実際のクラスではありません

def C(*args): 
    if len(args) == 1: 
     return CA(*args) 
    else: 
     return CB(*args) 

は、今、私たちは

C(1).foo() 
# A 
# mix 
C(1, 2).foo() 
# B 
# mix 

。なおCを持っていて:

は最後に、あなたはパラメータの数に基づいてCACBの間で選択するために便利な関数を書くことができますたとえば、isinstanceの第2引数として使用することはできません。

関連する問題