2

次の簡単なコードを使用してください。

class A{ 
  public: 
  virtual void foo() = 0; 
  void x(){ foo(); }
};
class B: public A{ foo(){ ... } };

main(){
  B b;
  b.x();
}

私が望むのは、派生クラスで実装されることを期待する関数を呼び出す関数を持つ抽象クラスを構築することです

問題は、私がそれを機能させることができないということです。コンパイラは、foo() への参照 (またはそのようなもの) が x() で実行されるのを見つけることができないため、コンパイルできないと言います基本クラス。これは機能しますか?誰かが私にこれの例を教えてもらえますか?

編集:「foo();」の場合は機能しないようです クラスA(ベースのもの)のデストラクタの中にあります...
それは私を混乱させました。=[

EDIT2:これはどれほど興味深いものでしたか。callfoo(){ foo(); を作成しました。これで問題なくコンパイルできますが、基本クラス A のデストラクタ内から純粋な抽象関数を直接呼び出そうとすると、エラーが発生します... 変です。誰でもこれについて何か考えがありますか?O_o

これについて何か助けてください。

ありがとう、
ジョナサン

アップデート

デストラクタの外で機能しました。今、私は混乱しました。

A(ベース)クラスのデストラクタ内に「foo()」を入れてみてください。少なくとも私はコンパイルしていません...

助けてください。

4

4 に答える 4

4

あなたがそれをするのを妨げるものは何もありません:

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

struct B : A {
    void f() { std::cout << "B::f()" << std::endl; }
};

// ...
A* a = new B;
a->g(); // prints "B::f()"

デストラクタ (またはコンストラクタ) から純粋仮想関数を呼び出す場合:しないでください! 未定義の動作を引き起こします。

§10.4/6 :

メンバ関数は、抽象クラスのコンストラクタ (またはデストラクタ) から呼び出すことができます。そのようなコンストラクタ (またはデストラクタ) から作成 (または破棄) されるオブジェクトに対して、直接的または間接的に純粋仮想関数への仮想呼び出し (10.3) を行うことの効果は定義されていません。

于 2010-04-05T00:17:40.563 に答える
1

いくつかの構文変更で動作するはずです。

#include <iostream>

class A { 
  public: 
  virtual ~A() {}
  virtual void foo() = 0; 
  void x() { foo(); }
};

class B: public A{ 
    void foo(){ std::cerr << "bingo!" << std::endl; } 
};

int main(){
  B b;
  b.x();
  return 0;
}

$ g++ -Wall -Weffc++ derived.cc 
$ ./a.out 
bingo!

この手法は完全に合法です。

于 2010-04-05T00:15:16.663 に答える
1

あなたが探しているのは、テンプレート メソッド パターンの実装のようです。

ポリモーフィズムを利用するには、ポインターを使用する必要があります (したがって、メッセージを回避します... x は B のメンバーではありません)

#include <iostream>                                                             

class A{  
  public: 
    virtual void foo() = 0;  
    virtual void x(){ foo(); }
};  
class B: public A{  
        void foo(){ std::cout<<"this is b"<<std::endl; } 
};

int main(){
 A* b= new B();
 b->x();

 return 0;
 }   
于 2010-04-05T00:19:29.417 に答える
0

理論的には問題なく機能しますが、クラス B の foo() に戻り値の型を追加する必要があります

于 2010-04-05T00:21:46.743 に答える