find_if error: invalid initialisation of reference of type 'const node&' from expression of type 'node*'
find_if error: invalid initialisation of reference of type 'const node&' from expression of type 'node*'
我有一个结构节点:
struct node {
node *parent;
int x, y;
float f, g, h;
};
我定义了一个谓词条件 bool 函数,用于查找结构成员是否已经存在于向量中。
bool Isinit(const node &nm, const node &ref)
{
if(nm.x==ref.x && nm.y==ref.y)
return true;
else
return false;
}
然后我这样调用函数:
vector<node*>::iterator referIt=find_if (open.begin(), open.end(), Isinit);
报错:
从 'node*' 类型的表达式对 'const node&' 类型的引用进行无效初始化。有人可以向我解释错误吗?
这是 cppreference.com 中 find_if
的可能实现:
template<class InputIt, class UnaryPredicate>
InputIt find_if(InputIt first, InputIt last, UnaryPredicate p)
{
for (; first != last; ++first) {
if (p(*first)) {
return first;
}
}
return last;
}
看起来你有一个 node*
的 vector
,因此,当你迭代和取消引用迭代器时,你传递给 p
的是一个 node*
但是不是 node&
元素。您可以更改函数以接受指针来解决此问题。另外,请参阅 find_if
实现接受 UnaryPredicate p
,因此您不能将接受两个参数的函数传递给它。
编辑:
解决此问题的另一种C++11
方法是使用functional
header中的bind
并将ref
绑定到Isinit
作为:
using namespace std::placeholders;
auto referIt = find_if (open.begin(), open.end(), std::bind(Isinit, _1, &ref));
您的代码有两个问题:参数数量和参数类型:
vector<node*>::iterator referIt =
find_if (open.begin(), open.end(), Isinit);
bool Isinit(const node &nm, const node &ref);
find_if
采用 一元 谓词。它将在每个元素上调用它,直到找到谓词 returns 为真的元素。该谓词必须接受容器中类型的 one 参数。根据您对 find_if
的调用,该类型是 node*
。因此,您的签名必须是:
bool Isinit(const node* nm);
现在这可能无法满足您的需求,因为您正在寻找 node*
来匹配您的 ref
,因此您需要编写一个仿函数:
struct Isinit {
const node* ref;
Isinit(const node*);
bool operator()(const node* nm); // compare passed-in 'nm'
// against member 'ref'
};
并这样称呼:
vector<node*>::iterator referIt =
find_if (open.begin(), open.end(), Isinit(ref));
其中,使用 C++11 lambda,都可以在线完成:
auto referIt = find_if(open.begin(), open.end(), [ref](const node* nm){
return nm->x == ref->x && nm->y == ref->y;
});
我有一个结构节点:
struct node {
node *parent;
int x, y;
float f, g, h;
};
我定义了一个谓词条件 bool 函数,用于查找结构成员是否已经存在于向量中。
bool Isinit(const node &nm, const node &ref)
{
if(nm.x==ref.x && nm.y==ref.y)
return true;
else
return false;
}
然后我这样调用函数:
vector<node*>::iterator referIt=find_if (open.begin(), open.end(), Isinit);
报错: 从 'node*' 类型的表达式对 'const node&' 类型的引用进行无效初始化。有人可以向我解释错误吗?
这是 cppreference.com 中 find_if
的可能实现:
template<class InputIt, class UnaryPredicate>
InputIt find_if(InputIt first, InputIt last, UnaryPredicate p)
{
for (; first != last; ++first) {
if (p(*first)) {
return first;
}
}
return last;
}
看起来你有一个 node*
的 vector
,因此,当你迭代和取消引用迭代器时,你传递给 p
的是一个 node*
但是不是 node&
元素。您可以更改函数以接受指针来解决此问题。另外,请参阅 find_if
实现接受 UnaryPredicate p
,因此您不能将接受两个参数的函数传递给它。
编辑:
解决此问题的另一种C++11
方法是使用functional
header中的bind
并将ref
绑定到Isinit
作为:
using namespace std::placeholders;
auto referIt = find_if (open.begin(), open.end(), std::bind(Isinit, _1, &ref));
您的代码有两个问题:参数数量和参数类型:
vector<node*>::iterator referIt =
find_if (open.begin(), open.end(), Isinit);
bool Isinit(const node &nm, const node &ref);
find_if
采用 一元 谓词。它将在每个元素上调用它,直到找到谓词 returns 为真的元素。该谓词必须接受容器中类型的 one 参数。根据您对 find_if
的调用,该类型是 node*
。因此,您的签名必须是:
bool Isinit(const node* nm);
现在这可能无法满足您的需求,因为您正在寻找 node*
来匹配您的 ref
,因此您需要编写一个仿函数:
struct Isinit {
const node* ref;
Isinit(const node*);
bool operator()(const node* nm); // compare passed-in 'nm'
// against member 'ref'
};
并这样称呼:
vector<node*>::iterator referIt =
find_if (open.begin(), open.end(), Isinit(ref));
其中,使用 C++11 lambda,都可以在线完成:
auto referIt = find_if(open.begin(), open.end(), [ref](const node* nm){
return nm->x == ref->x && nm->y == ref->y;
});