从 lambda 表达式返回布尔值时出错
Error while returning boolean from lambda expressions
bool markersFormRectangle = [](std::vector<cv::Point2f> markerCoords) {
cv::Point2f center(
(markerCoords[0].x + markerCoords[1].x + markerCoords[2].x + markerCoords[3].x) / 4,
(markerCoords[0].y + markerCoords[1].y + markerCoords[2].y + markerCoords[3].y) / 4
);
float dd1 = cv::norm(center - markerCoords[0]);
float dd2 = cv::norm(center - markerCoords[1]);
float dd3 = cv::norm(center - markerCoords[2]);
float dd4 = cv::norm(center - markerCoords[3]);
return (fabs(dd1-dd2) < 5) && (fabs(dd1 - dd3) < 5) && (fabs(dd1 - dd4) < 5);
};
我正在尝试使用上述 lambda 表达式来检查四个点是否形成近矩形。但是编译器抱怨错误:当我尝试通过以下方式在 if 语句中使用 lambda 表达式时,调用的对象类型 'bool' 不是函数或函数指针:
if (markersFormRectangle(markerPoints)) {
//do something
}
当我更改返回类型auto
时,它不会给我该错误。我对使用 lambda 函子很陌生。你能告诉我我做错了什么,以及为什么如果类型更改为auto
编译器不再给出错误?
在此声明中
bool markersFormRectangle = [](std::vector<cv::Point2f> markerCoords)
{
cv::Point2f center((markerCoords[0].x +markerCoords[1].x + markerCoords[2].x + markerCoords[3].x) / 4,
(markerCoords[0].y +markerCoords[1].y + markerCoords[2].y + markerCoords[3].y) / 4);
float dd1 = cv::norm(center - markerCoords[0]);
float dd2 = cv::norm(center - markerCoords[1]);
float dd3 = cv::norm(center - markerCoords[2]);
float dd4 = cv::norm(center - markerCoords[3]);
return (fabs(dd1-dd2) < 5) && (fabs(dd1 - dd3) < 5) && (fabs(dd1 - dd4) < 5);
};
初始值设定项是一个 lambda 表达式,而声明的变量具有 bool 类型。没有从 lambda 表达式类型到类型bool
的隐式或上下文相关转换。
考虑到每个 lambda 都有自己独特的类型。
所以你必须写
auto markersFormRectangle = [](std::vector<cv::Point2f> markerCoords)
{
cv::Point2f center((markerCoords[0].x +markerCoords[1].x + markerCoords[2].x + markerCoords[3].x) / 4,
(markerCoords[0].y +markerCoords[1].y + markerCoords[2].y + markerCoords[3].y) / 4);
float dd1 = cv::norm(center - markerCoords[0]);
float dd2 = cv::norm(center - markerCoords[1]);
float dd3 = cv::norm(center - markerCoords[2]);
float dd4 = cv::norm(center - markerCoords[3]);
return (fabs(dd1-dd2) < 5) && (fabs(dd1 - dd3) < 5) && (fabs(dd1 - dd4) < 5);
};
来自 C++14 标准(5.1.2 Lambda 表达式)
3 lambda 表达式的类型(这也是 闭包对象)是一个唯一的、未命名的非联合类类型,称为 闭包类型 — 其属性如下所述。此类类型 既不是聚合 (8.5.1) 也不是文本类型 (3.9)。
要显式指定 lambda 返回类型,您可以使用尾随返回类型说明符编写
auto markersFormRectangle = [](std::vector<cv::Point2f> markerCoords) -> bool
{
cv::Point2f center((markerCoords[0].x +markerCoords[1].x + markerCoords[2].x + markerCoords[3].x) / 4,
(markerCoords[0].y +markerCoords[1].y + markerCoords[2].y + markerCoords[3].y) / 4);
float dd1 = cv::norm(center - markerCoords[0]);
float dd2 = cv::norm(center - markerCoords[1]);
float dd3 = cv::norm(center - markerCoords[2]);
float dd4 = cv::norm(center - markerCoords[3]);
return (fabs(dd1-dd2) < 5) && (fabs(dd1 - dd3) < 5) && (fabs(dd1 - dd4) < 5);
};
虽然没有必要。
请记住(5.1.2 Lambda 表达式)
7 lambda表达式的复合语句产生函数体 (8.4)的函数调用运算符,...
Lambda 只能存储在auto
类型的变量中或转换为函数指针(例如使用std::function
),如果你想得到你的 lambda 的结果,你需要称之为 fist。您的代码应为:
auto markers = []{ return true; };
bool value = markers();
或
bool value = []{ return true; }();
取决于您是尝试存储 lambda 还是其结果。
相关文章:
- 在没有定义返回类型的函数中返回布尔值,并将结果保存在无错误的char编译中-为什么
- 变量定义到C++布尔值转换
- 如何确保在使用基于布尔值的两个方法之一调用方法时避免分支预测错误
- 重载更少,则运算符返回相反的布尔值
- 将此布尔值传递给此函数的最有效方法是什么?
- 如何设置 c++ 类的布尔值?
- 使用 MAKEWORD / MAKEWPARAM 使用布尔值而不是布尔值
- 将 10 个线程与原子布尔值同步
- 创建类似于布尔值的变量类型
- 布尔值向量的基于范围 for 循环
- 零点和布尔值之间的比较
- 简化对两个布尔值的 4 个 if/else 检查
- 无法创建带有布尔值和矢量的地图
- 对于完成布尔值设置为 true 后未停止的循环
- fstream / ifstream / ofstream 对象如何转换为布尔值
- C++:将值赋值给原始数据类型(例如布尔值)是原子操作吗?
- 为什么布尔值不能比作最后一点?
- 从 lambda 表达式返回布尔值时出错
- 关闭文件流时出错,其存在取决于与 C++ 中的 .close() 语句相同的布尔值
- 在 C++ 中使用布尔值时出错