4

g++ から奇妙なコンパイラ エラーが発生します。

エラーが発生した場所を含めておらず、使用していませstd::plus is not a functionんが、次のコードには「 」と表示されています。<functional>std

コードは次のとおりです。

#include <iostream>

template<class T1, class T2, class T3>
struct MyStruct {
  T1 t1; T2 t2; T3 t3;
  MyStruct() {}
  MyStruct(T1 const& t1_, T2 const& t2_, T3 const& t3_)
    : t1(t1_), t2(t2_), t3(t3_) {}
};

template<class T1, class T2, class T3>
MyStruct<T1, T2, T3> plus(MyStruct<T1, T2, T3> const& x,
              MyStruct<T1, T2, T3> const& y) {
  // ...
}

int main() {
  typedef MyStruct<int, double, std::string> Struct;
  Struct x(2, 5.6, "bar");
  Struct y(6, 4.1, "foo");
  Struct result = plus(x, y);
}

完全なエラーは次のとおりです (わずかに再フォーマットされています)。

/usr/include/c++/4.2.1/bits/stl_function.h: In function 'int main()':
/usr/include/c++/4.2.1/bits/stl_function.h:134:
    error: 'template<class _Tp> struct std::plus' is not a function,
plus3.cc:13: error:
   conflict with 'template<class T1, class T2, class T3> 
     MyStruct<T1, T2, T3> plus(const MyStruct<T1, T2, T3>&, 
       const MyStruct<T1, T2, T3>&)'
plus3.cc:21: error:   in call to 'plus'

これがなぜなのか、エラーを回避する方法を知っている人はいますか? 関数を呼び出したいのですがplus

plus関数に 3 つのテンプレート引数がない場合、エラーは発生しませんstd::plus

  template <class _Tp>
    struct plus : public binary_function<_Tp, _Tp, _Tp>

std::plusしかし、その時点でさえ知られるべきではないので、それはまだ奇妙です.

アップデート:

いくつかの回答に応じて、エラーが発生するわずかに変更されたコードを貼り付けます。私のplus関数はnamespace fooここにあり、同じ名前空間から呼び出されるため、次を使用して修飾する必要はありませんfoo::

#include <string>

namespace foo {

template<class T1, class T2, class T3>
struct MyStruct {
  T1 t1; T2 t2; T3 t3;
  MyStruct() {}
  MyStruct(T1 const& t1_, T2 const& t2_, T3 const& t3_)
      : t1(t1_), t2(t2_), t3(t3_) {}
};

template<class T1, class T2, class T3>
MyStruct<T1, T2, T3> plus(MyStruct<T1, T2, T3> const& x,
                          MyStruct<T1, T2, T3> const& y) {
  // ...                                                                                                                        
}

template<class T1, class T2, class T3>
MyStruct<T1, T2, T3> bar(MyStruct<T1, T2, T3> const& x,
                         MyStruct<T1, T2, T3> const& y) {
  return plus(x, y);
}

} // end foo                                                                                                                    

int main() {
  typedef foo::MyStruct<int, double, std::string> Struct;
  Struct x(2, 5.6, "bar");
  Struct y(6, 4.1, "foo");
  Struct result = foo::bar(x, y);
}
4

3 に答える 3

5

std::plus は関数ではないためです。

関数 plus はグローバル名前空間にあるため、行う必要があります

Struct result = ::plus(x, y);

std::plus を使用しようとしている理由は、必要な plus のバージョンで明示的でなかったため、コンパイラは引数を介して plus を見つけるKoenig ルックアップを使用したためです。

于 2012-05-22T20:43:56.883 に答える
0

関数を別の名前空間に配置すると、このエラーは発生しません。これが名前空間の目的です。衝突を引き起こすことなく、異なる名前空間で同じシンボル/署名を持つことができます。

于 2012-05-22T20:40:46.227 に答える
0

plus() 明示的に名前空間を指定してみてください

Struct result = ::plus(x, y);

これは gcc に役立ち、 plus() を別の名前空間に配置する必要はありません。

ロキ・アスタリが残りを語る

于 2012-05-22T20:37:55.947 に答える