0

ポリモーフィズムと親子関係に問題があります。次の2つのクラスを受講し、私のアプリケーションで「子」のオブジェクトを作成すると想像してください。オブジェクトの外では、私が呼び出す唯一の関数はupdate()であり、これはオブジェクト内で必要な他のすべてを呼び出します。この一連の呼び出しで「親」と「子」が異なる唯一の関数はdosomething2()です。

class parent 
{
    public:
        void dosomething1() {}; //amongst other things, calls dosomething2
        void dosomething2() {};
        void update() {}; //amongst other things, calls dosomething1
}

class child : public parent
{
    void dosomething2() {}
}

'child'のオブジェクトを作成してupdate()を呼び出すと、親クラスの関数のみが呼び出されることに気付きました。update()とdosomething1()を子クラスにコピーする必要がありましたが、すべてが期待どおりに機能しました。重複コードがたくさんあるので、それはあまり良い解決策ではありません-これを改善する方法はありますか?

更新: 提供された回答のおかげで、仮想dosomething2()関数で親クラスを更新しました。これで正しい関数が呼び出され、dosomething1()を子クラスにコピーする必要はありません。残念ながら、update()を子クラスにコピーしないと、シンボルルックアップエラーが発生します(親と子の両方が一緒にライブラリにあります)。

class parent 
{
    public:
        void dosomething1() {}; //amongst other things, calls dosomething2
        virtual void dosomething2() {};
        void update() {}; //amongst other things, calls dosomething1
}

class child : public parent
{
    void dosomething2() {}
    /*void update() {}; //symbol lookup error if this is left uncommented */
}

UPDATE2 シンボルルックアップエラーはコードに関連していませんでした。私はmakecleanを実行し、次にmake(.soライブラリと実行可能ファイルをビルドします)を実行しました。これで、期待どおりに動作します。

4

3 に答える 3

3

基本クラスの関数を仮想としてマークしていません。

class parent 
{
    public:
        virtual void dosomething1() {}; //amongst other things, calls dosomething2
        virtual void dosomething2() {};
        void update() {}; //amongst other things, calls dosomething1
}

また、参考までに、あなたがしていることはテンプレートメソッドパターンと呼ばれています。

于 2012-08-28T06:17:24.493 に答える
2

virtual必要に応じて、親クラスでキーワードを使用する必要がありますdynamic-polymorphism。次に、子クラスで仮想関数を再実装するか、再実装しないでください。

class parent 
{
    public:
        void dosomething1() {}; //amongst other things, calls dosomething2
        virtual void dosomething2() {};
        void update() {}; //amongst other things, calls dosomething1
}
于 2012-08-28T06:18:06.247 に答える
1

関連する機能を作成する必要がありますvirtual。あなたがchild'sdoSomething1()を望み、doSomething2()への呼び出しから呼び出されると仮定しますupdate()

class parent 
{
    public:
        virtual void dosomething1() {}; //amongst other things, calls dosomething2
        virtual void dosomething2() {};
        void update() {}; //amongst other things, calls dosomething1
}

class child : public parent
{
    virtual void dosomething2() {}
}

次に、child'supdate()を呼び出すと、可能な場合は派生クラス'メソッドが呼び出されます。child`をupdate() is not virtual, so you should have no filed called更新しないと、その名前が非表示になることに注意してください。in

于 2012-08-28T06:18:22.970 に答える