0

基本クラスを持ち、std::listいくつかの型のサブクラスを入れて、子クラスのメンバーに繰り返しアクセスすることは可能ですか?

4

3 に答える 3

1

はい、可能ですが、スライシングの問題を回避するために、値の代わりにポインターを保存してください。

#include <iostream>
#include <list>

struct Base {
  virtual ~Base() {}
  virtual void f() = 0;
};

struct DerivedA : Base {
  virtual void f() { std::cout << "DerivedA::f\n"; }
};

struct DerivedB : Base {
  virtual void f() { std::cout << "DerivedB::f\n"; }
};

int main()
{
  std::list<Base *> l;
  l.push_back( new DerivedA );
  l.push_back( new DerivedB );

  for ( std::list<Base *>::const_iterator it = l.begin(); it != l.end(); ++it ) {
    (*it)->f();
  }
}

これは印刷します

DerivedA::f
DerivedB::f

生のポインターを格納する代わりに、適切に呼び出しを処理するある種のスマート ポインターを使用することをお勧めdeleteします。C++11 にはさまざまなスマート ポインターがありますが、std::auto_ptr は使用しないでください。

于 2013-08-15T14:28:52.570 に答える
0

スライスのために置くことはできませんがDerived、ポインター(またはよりスマートなポインター)を使用して行うことができます。std::list<Base>

std::list<Base*> l;
l.push_back(new Derived); // don't forget to delete it!!

あなたが呼び出すことができます(*l.begin())->method_that_present_in_base()。このメソッドが仮想の場合、派生のメソッドが呼び出されます。

例:

#include <iostream>
#include <list>

struct Animal {
    virtual void say() {
        std::cout <<"I'm generic animal\n";
    }

    virtual ~Animal(){}
};

struct Cat : public Animal {
    virtual void say() {
        std::cout << "Meow\n";
    }
    virtual ~Cat(){}
};

int main() {
    std::list<Animal*> l;
    l.push_back(new Animal);
    l.push_back(new Cat);
    for(Animal* ptr: l) {
        ptr->say();
    }
    for(Animal* ptr: l) {
        delete ptr; //not needed if you use smart pointers.
    }
}

出力

私は一般的な動物
ニャーです

于 2013-08-15T14:29:12.557 に答える