2011-12-16 5 views
0

私はここで何をしたいのか正確に説明するのは難しいですが、私は基本クラスとこの基本クラスを継承する2つのクラスを持っています。それを継承する両方のクラスには、独自のメンバーがあります。私はメソッドに両方を渡すことができるようにしたい、そして、そのメソッドがそれを検出して、それらのユニークなメンバーにアクセスするようにしたい。私はそれを継承する2つのクラスだけがあると仮定することはできませんので、私はより一般的な解決策の何かを探しています。メソッドにクラスを渡す方法とベースクラスから継承を検出する方法は?

#include <iostream> 

class Base { 

    public: 
    int _type; 
    Base() { } 
}; 

class First : public Base { 
    public: 
    int _first_only; 

    First() { } 
}; 

class Second : public Base { 
    public: 
    int _second_only; 

    Second() { } 
}; 

void test (Base b) { 

    std::cout << "Type: " << b._type << std::endl; 

    if(b._type==1) { 
    std::cout << "First\n"; 
    // Want to be able to do this 
    std::cout << "Val: " << (First)b._first_only << std::endl; 
    } else if(b._type==2) { 
    std::cout << "Second\n"; 
    // And this 
    std::cout << "Val: " << (Second)b._second_only << std::endl; 
    } 
} 

int main() { 

    First f; 
    f._first_only=1; 
    f._type=1; 
    Second s; 
    s._type=2; 
    s._second_only=2; 

    test(f); 
    test(s); 
} 

答えて

1

これは、他の人の答えのようになります。

  1. あなたは仮想関数を使用して、この動作を取得するために多型クラスを書くことができます。
  2. ポインタまたは参照によってDerviedクラスオブジェクトを渡して、多態性の動作を取得します。それ以外の場合は、オブジェクトのスライスにつながります。 test()関数はオブジェクトをスライスします。

このコードも役に立ちます。タイプを印刷するさまざまな方法があることがわかります。私はGetBaseType()、GetDerivedType()、GetType()を使用しました。これらの中でGetType()メソッドはあなたにとって大変便利です。便宜上、2つのコンストラクタがあります。コンストラクターはデータメンバーを初期化できます。

class Base { 
private: 
    int _type; 
public: 
    Base(int type) : _type(type) { } 
    int GetBaseType() { return _type; } 
    virtual int GetDerivedType() = 0; 
    virtual int GetType() { return _type; } 
}; 

class First : public Base { 
private: 
    int _first_only; 
public: 
    First() : Base(1), _first_only(1) { } 
    First(int first_only) : Base(first_only), _first_only(first_only) { } 
    int GetDerivedType() { return _first_only; } 
    virtual int GetType() { return _first_only; } 
}; 

class Second : public Base { 
private: 
    int _second_only; 
public: 
    Second() : Base(2), _second_only(2) { } 
    Second(int second_only) : Base(second_only), _second_only(second_only) { } 
    int GetDerivedType() { return _second_only; } 
    virtual int GetType() { return _second_only; } 
}; 

void test (Base &b) { 
    std::cout << "Type: " << b.GetBaseType() << std::endl; 
    std::cout << "Type: " << b.Base::GetType() << std::endl; 

    std::cout << "Dervied type: \n"; 
    std::cout << "Val: " << b.GetDerivedType() << std::endl; 
    std::cout << "Val: " << b.GetType() << std::endl; 
} 

int main() { 

    First f(1); 
    Second s(2); 

    test(f); 
    test(s); 

    First f1; 
    Second s1; 

    test(f1); 
    test(s1); 
} 
1
  1. どちらかがBaseFirstSecondから共通の部材の種類を移動しBase
  2. virtual関数を宣言:ここ

    は私がやりたいものの一例です。あなたの特定の問題については

、第二の選択肢は、より良いです:

class Base { 
    public: 
    int _member; // have getter() method, if '_member' is private 
    Base() { } 
}; 

内部では、test()

void test (Base &b) { // <--- practice to pass by reference if copy is not needed 
    // use b._member; 
}; 
1

あなたがして、関数パラメータを渡しているので、あなたのコードは、多態動作しません。スライスします。

異なるタイプのメソッドを使用する場合は、これらのタイプごとにオーバーロードすることを検討してください。私がやるだろう

0

3つのこと:タイプコードの一般的なスイッチングに

  • は良いオブジェクト指向設計とはみなされません。代わりにクラスに切り替えるコードを引っ張ります。
  • また、特定のクラスのコンストラクタにtypeタグを設定します。
  • 他の人が触れたように、スライシングを避けるために、引数を渡す必要があります。ここで

は、コードは次のようになります:

#include <iostream> 

class Base { 

    public: 
    int _type; 
    Base() { } 
    virtual void print_to_stream(std::ostream & os) const =0; 
}; 

class First : public Base { 
    public: 
    int _first_only; 

    First() { _type =1; } 
    void print_to_stream(std::ostream & os) const 
    { 
     os<<"First\n"; 
     os<<"Val: " << _first_only << std::endl; 
    } 
}; 

class Second : public Base { 
    public: 
    int _second_only; 

    Second() { _type=2; } 

    void print_to_stream(std::ostream & os) const 
    { 
     os << "Second\n"; 
     os << "Val: " << _second_only << std::endl; 
    } 
}; 

void test (Base & b) 
{ 
    std::cout << "Type: " << b._type << std::endl; 
    b.print_to_stream(std::cout); 
} 

int main() { 
    First f; 
    f._first_only=1; 
    Second s; 
    s._second_only=2; 

    test(f); 
    test(s); 
} 
関連する問題