"エラー:不完全なクラス型へのポインタは許可されません。"の前方宣言。
2022-02-13 17:52:11
C++のファイルをコンパイルする際、forward declarationを使用しているため、この問題に遭遇することがあります。
wikiの定義からすると、コンピュータ・プログラミングにおいて、前方宣言とは、まだ完全に定義されていない識別子(データ型、変数、関数などプログラミングを表す実体)を宣言することである。
例えばClassA.h
#pragma once
classB;
classClassA
{
public:
ClassA(void);
~ClassA(void);
public:
void Fun(ClassB & classB);
public:
ClassB * m_classB;
};
ClassA には ClassB * 型のメンバ変数がありますが、ClassB は完全には定義されていないので、ClassB の宣言のみを与えています;,class ClassB は Incompete 型です。
C++では、完全型と不完備型の違いがあります。完全型はコンパイル時にサイズを決定できるが、不完全型はコンパイル時にサイズを決定できない。したがって、Incomplete型は、その型のオブジェクトを定義することはできず、その型へのポインタや参照を定義したり、その型を正式な参照型や戻り型として使用する関数を宣言(定義ではない)するためにのみ使用できる、限られた方法でのみ使用することができるのです。
通常、AとBの2つのクラスを宣言したとします。A.hにBクラスのオブジェクトを定義する必要がある場合、B b;は #include "B.h"; を、BクラスにAクラスのオブジェクトを定義する必要がある場合はA a; に B.h を含めるように縛ります。しかし相互参照といって、インクルードは許されず、ここで前向き宣言が使用されるのです。
上記の例に倣い、完全なコードは以下の通りです。
クラスA.cpp
#include "ClassA.h"
#include "ClassB.h"//because ClassA.h uses the forward declaration of ClassB, ClassB.h needs to be included here to get all the information about ClassB.
ClassA::ClassA(void)
{
}
ClassA::~ClassA(void)
{
}
void ClassA::Fun(ClassB & classB)
{
m_classB = &classB;
int v = m_classB-> GetValue();
}
クラスB.h
#pragma once
#include "ClassA.h"
classB
{
public:
ClassB(void);
~ClassB(void);
public:
int GetValue() const { return m_Value; }
void SetValue(int val) { m_Value = val; }
private:
int m_Value;
};
クラスB.cpp
#include "ClassB.h"
ClassB::ClassB(void)
{
m_Value = 123;
}
ClassB::~ClassB(void)
{
}
前方宣言は相互参照のジレンマを解決し、またコンパイル速度をある程度向上させることができます。それが、前方宣言を必要とする主な理由です。
関連
-
vs2015 はソースファイル stdio.h を見つけることができない 解決策
-
c++11の機能を含むcmakeの書き方 (-std=c++11 cmakeList.txtに書き込む方法)
-
C++プリントベクター
-
エラー: "***"の前にイニシャライザーがあります。
-
error: label 'xxxxxxx' [-fpermissive] にジャンプします。
-
警告:組み込み関数 'malloc' の互換性のない暗黙の宣言を修正する方法
-
c++ 11 random ライブラリの簡単な使い方
-
C++ shared_ptr コンパイルエラー 'shared_ptr' がこのスコープで宣言されていない問題を修正しました。
-
ベクター使用時、ベクター添え字が範囲外、その他類似のエラーが発生する。
-
デバッグエラー Assertion Failed 問題について
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
C++ std::string は NULL で初期化できない、基本的な使い方
-
戦闘機ゲームのC++実装(ソースコード)
-
C/C++共通エラーの概要
-
error: 'vector' does not name a type
-
34:5: エラー: 制御が非ボイド関数の終わりに達する可能性がある [-Werror,-Wreturn-type] エラー解析
-
C++のコンパイルエラーで修飾子が破棄される [-fpermissive] 。
-
C++ [エラー] 'std::string {aka std::basic_string<char>}' を 'char*' に変換できないエラー
-
const char*' から 'char*' への変換が無効です。
-
gccコンパイルエラーの一覧
-
[エラー]'cout' はこのスコープで宣言されていません。