2017-05-04 6 views
0

検索は実行しましたが、クエリに一致するものは見つかりませんでした。1つのテンプレートクラスから別のテンプレートクラスへの変換演算子

テンプレートクラス(Vector2、Vector3、Vector4)があります。

エラーC2833:Visual Studioの2017を使用して2および4に3と4、 とのVector3にベクトル2から変換演算子を定義しようと など

template <typename T> 
class Vector4 { 
    // ... 
    operator Vector2<T>() const { return { x, y }; } 
    operator Vector3<T>() const { return { x, y, z }; } 
    // ... 
    T x, y, z, w; 
    // ... 
} 


template <typename T> 
class Vector3 { 
    // ... 
    operator Vector2<T>() const { return { x, y }; } 
    operator Vector4<T>() const { return { x, y, z, 0 }; } 
    // ... 
    T x, y, z; 
    // ... 
} 


template <typename T> 
class Vector2 { 
    // ... 
    operator Vector3<T>() const { return { x, y, 0 }; } 
    operator Vector4<T>() const { return { x, y, 0, 0 }; } 
    // ... 
    T x, y; 
    // ... 
} 

は私にこれを提供します「演算子をVector2 'は認識されていない演算子またはタイプではありません

すべて、すべての援助をいただきありがとうございます。

ありがとうございます。

編集:実際のソースには、クラス定義の後にセミコロンがあります。私が投稿した簡単なバージョンにそれらを入れるのを忘れてしまった。 はまた、はい、多くのエラーがあったが、私の経験では、それは通常 が宣言前進しようとした重要な最初のものです:

template <class T> class Vector 3; 
template <class T> class Vector 4; 

template <typename T> 
class Vector2 { 
// ... 
} 

編集:今、私は取得エラーC2988:認識できないテンプレート宣言/定義。おそらく、3つのテンプレートクラスが別々のファイルにあることに言及する価値はあります。私はもともとタイプ変換演算子を働かせるためにただ1つのクラスにヘッダを含めようとしましたが、これはオリジナルのエラーを与えていたものです。

ああ、はい。私は間違いなくそれらを明示的にしています。それは常に良いアドバイスです。しかし0430のローカルタイムでした。:)

編集:Nevermind、私はspazです。私はVectorとdimsの数の間にどのようにスペースを入れたのかわかりません "Vector 2"!= "Vector2"。フォワード宣言はそれでした。私はとても簡単なことを逃したとは信じられません。 子供たち:あなたが結ばれたときには、コードはしないでください。

+0

あなたはこれらの演算子を宣言する検討する必要があります[ '明示的]](http://en.cppreference.com/w/cpp/language/explicit)。 –

+0

それだけではなく、もっと多くのエラーメッセージが表示されるはずです。私はあなたが少なくとも10を得るべきであることがわかります...クラス定義をセミコロンで閉じます。コンパイラは宣言される前に型を認識できません。 –

答えて

1

Vector4<T>::operator Vector2<T>() const;を宣言すると、宣言される前にクラスVector2<T>が使用されています。 Vector4<T>::operator Vector3<T>() const;でも同じことが起こります。フォワードはあなたのクラスを先に宣言します。

// Forward declarations 
template<class T> class Vector2; 
template<class T> class Vector3; 

template <typename T> 
class Vector4 { 
    // ... 
    operator Vector2<T>() const { return{ x, y }; } 
    operator Vector3<T>() const { return{ x, y, z }; } 
    // ... 
    T x, y, z, w; 
    // ... 
}; 


template <typename T> 
class Vector3 { 
    // ... 
    operator Vector2<T>() const { return{ x, y }; } 
    operator Vector4<T>() const { return{ x, y, z, 0 }; } 
    // ... 
    T x, y, z; 
    // ... 
}; 


template <typename T> 
class Vector2 { 
    // ... 
    operator Vector3<T>() const { return{ x, y, 0 }; } 
    operator Vector4<T>() const { return{ x, y, 0, 0 }; } 
    // ... 
    T x, y; 
    // ... 
}; 
+0

ありがとうございます。それがそれでした。私はそれを逃したと信じられない。 –

0

あなたは循環依存関係にあります。
変換コンストラクタを1つの「方向」に使用して解決できます。
この1つはそれらを減少させるための寸法を増大させるためのコンストラクタ、変換演算子を使用しています。

template <typename T> 
class Vector2 { 
    T x, y; 
}; 

template <typename T> 
class Vector3 { 
    Vector3(const Vector2<T>& v2) : x(v2.x), y(v2.y), z(0) {} 
    operator Vector2<T>() const { return { x, y }; } 
    T x, y, z; 
}; 

template <typename T> 
class Vector4 { 
    Vector4(const Vector2<T>& v2) : x(v2.x), y(v2.y), z(0), w(0) {} 
    Vector4(const Vector3<T>& v3) : x(v3.x), y(v3.y), z(v3.z), w(0) {} 
    operator Vector2<T>() const { return { x, y }; } 
    operator Vector3<T>() const { return { x, y, z }; } 
    T x, y, z, w; 
}; 

(ここでは暗黙の型変換の危険についての挿入厳しい警告。)

+0

私はフランソワ・アンドリューの答えを正しいものとしてマークしましたが(循環依存性の問題よりも前方宣言のほうが多かったようですが)、私の好きなソリューションについてある程度の優雅さがあり、使用して終了します。あなたのおかげで両方。私は100%同意するので、コンバージョンを明示的にしました。他の人のコードを使用しているときに予期せぬ変換に何度も驚いています。 –

関連する問題