最近、次の問題に遭遇したときに、C++ でラムダを使用する方法を学んでいます。
テンプレート化された変数をキャプチャするラムダを作成すると (参照またはコピーは関係ありません)、ラムダ自体とは関係なく、奇妙なコンパイル エラーが発生します。テストコードは次のとおりです。
// templated.cpp
#include <iostream>
#include <vector>
template<class T, class Function>
Function for_each_index(const T& v, Function f)
{
for (unsigned int i = 0; i < v.size(); ++i) { f(i); }
return f;
}
class Test
{
public:
template<class T>
T f() { return 1; }
};
template<class T>
void fun(T& v)
{
for_each_index(v, [&v] (unsigned int i) {
v[i].f<float>();
});
}
int main()
{
std::vector<Test> v;
v.push_back(Test());
v.push_back(Test());
v.push_back(Test());
fun(v);
return 0;
}
上記のコードのコンパイルは、次のメッセージで失敗します。
$ g++ -Wall templated.cpp -std=c++0x
templated.cpp: In lambda function:
templated.cpp:23:16: error: expected primary-expression before ‘float’
templated.cpp:23:16: error: expected ‘;’ before ‘float’
ただし、ラムダをmain
(テンプレートがない) に移動すると、問題なくコンパイルされます。
// simple.cpp
#include <iostream>
#include <vector>
template<class T, class Function>
Function for_each_index(const T& v, Function f)
{
for (unsigned int i = 0; i < v.size(); ++i) { f(i); }
return f;
}
class Test
{
public:
template<class T>
T f() { return 1; }
};
int main()
{
std::vector<Test> v;
v.push_back(Test());
v.push_back(Test());
v.push_back(Test());
for_each_index(v, [&v] (unsigned int i) {
v[i].f<float>();
});
return 0;
}
for_each_index
私自身のコードで同様の「反復ツール」を使用しているため、ここで使用します。これにより、上記のエラーが発生します(元のコードは重い画像処理を行います。このコードは概念の証明です)。ただし、ここでは 2 番目の目的を果たします。つまり、テンプレート化された変数をラムダ引数に入れないようにすることです。
それで、これはコンパイラのバグですか?それとも、私は何か非常に間違ったことをしていますか? もしそうなら、どのような回避策を提案できますか?
参考までに、私は標準の Ubuntu-issue g++
、 versionを使用してい4.6.3
ます。