メインコンテンツ

このページの内容は最新ではありません。最新版の英語を参照するには、ここをクリックします。

MISRA C++:2008 Rule 10-3-1

There shall be no more than one definition of each virtual function on each path through the inheritance hierarchy.

説明

ルール定義

There shall be no more than one definition of each virtual function on each path through the inheritance hierarchy. 1

根拠

チェッカーは、継承階層内の同じパスに複数の定義をもつバーチャル メンバー関数にフラグを設定します。関数が複数回定義されている場合、特定の関数呼び出しで使用される実装があいまいになる可能性があります。

Polyspace 実装

チェッカーは、基底クラスのメンバー関数が virtual キーワードを使用せずに派生クラスで再定義されている場合にも違反を報告します。

トラブルシューティング

ルール違反が想定されるものの、Polyspace® から報告されない場合は、コーディング規約違反が想定どおりに表示されない理由の診断を参照してください。

すべて展開する

class Base {
    public:
      virtual void foo() {
     }
};

class Intermediate1: public virtual Base {
    public:
      virtual void foo() { //Noncompliant
      }    
};

class Intermediate2: public virtual Base {
    public:
       void bar() {
          foo();  // Calls Base::foo()
      }    
};

class Final: public Intermediate1, public Intermediate2 {
};

void main() {
    Intermediate2 intermediate2Obj;
    intermediate2Obj.bar(); // Calls Base::foo()
    Final finalObj;
    finalObj.bar(); //Calls Intermediate1::foo() 
                    //but you might expect Base::foo()
}

この例では、virtual 関数 foo が基底クラス Base に加え、派生クラス Intermediate1 でも定義されています。

混乱の原因になる可能性があるのは以下のとおりです。クラス Final は、Intermediate1 から派生していながら、Intermediate2 を使った別のパスを介して Base からも派生しています。

  • Intermediate2 のオブジェクトで、関数 foo の呼び出しを行う関数 bar を呼び出すと、Basefoo の実装が呼び出されます。Intermediate2 のオブジェクトは Intermediate1 の実装は把握していません。

  • しかし、Final のオブジェクトで、関数 foo の呼び出し行う同じ関数 bar を呼び出すと、より下流の派生クラスが優先されるため、Intermediate1foo の実装が呼び出されます。

この動作を考慮に入れていない場合、予期しない結果になる可能性があります。

この問題を防ぐには、基底クラスで関数を純粋バーチャル関数として宣言します。たとえば、クラス Base を次のように宣言できます。

class Base {
    public:
      virtual void foo()=0;
};

void Base::foo() {
      //You can still define Base::foo()
}

チェック情報

グループ: Derived Classes
カテゴリ: 必要

バージョン履歴

R2013b で導入


1 All MISRA coding rules and directives are © Copyright The MISRA Consortium Limited 2021.

The MISRA coding standards referenced in the Polyspace Bug Finder™ documentation are from the following MISRA standards:

  • MISRA C:2004

  • MISRA C:2012

  • MISRA C:2023

  • MISRA C++:2008

  • MISRA C++:2023

MISRA and MISRA C are registered trademarks of The MISRA Consortium Limited 2021.