返回信息流```C\C++
#include "stdafx.h"
#include "opencv2/highgui/highgui.hpp"
#include "opencv2/imgproc/imgproc.hpp"
#include <iostream>
#include <algorithm>
#include <vector>
#include<set>
#include <utility>
using namespace cv;
using namespace std;
Mat g_srcImage, g_grayImage;
#define WINDOW_NAME "【角点检测】"
int _tmain(int argc, _TCHAR* argv[])
{
// 载入源图像
g_srcImage = imread("\\vmware-host\\Shared Folders\\桌面\\left4.jpg");
// 双边滤波
Mat out;
bilateralFilter(g_srcImage, out, 25, 25 * 2, 25 / 2);
// 转换成灰度图
cvtColor(out, g_grayImage, COLOR_BGR2GRAY);
// 角点检测
vector<Point> corners;
double qualityLevel = 0.01;//角点检测可接受的最小特征值
double minDistance = 10;//角点之间的最小距离
int blockSize = 3;//计算导数自相关矩阵时指定的邻域范围
double k = 0.04;//权重系数
Mat copy = g_srcImage.clone(); //复制源图像到一个临时变量中,作为感兴趣区域
int cornerNum = 30;
// 进行Shi-Tomasi角点检测
goodFeaturesToTrack(g_grayImage,//输入图像
corners,//检测到的角点的输出向量
cornerNum,//角点的数量
qualityLevel,//角点检测可接受的最小特征值
minDistance,//角点之间的最小距离
Mat(),//感兴趣区域
blockSize,//计算导数自相关矩阵时指定的邻域范围
false,//不使用Harris角点检测
k);//权重系数
cornerNum = corners.size();
int distNum = 0;
while (corners.size()>1)
{
double minDist = 1000;
int minDistNum = 0;
for (int i = 0; i < corners.size(); i++)
{
double distance = powf((corners[i].x - corners[distNum].x), 2) + powf((corners[i].y -corners[distNum].y), 2);
distance = sqrtf(distance);
if (distance < minDist && distance > 0)
{
minDist = distance;
minDistNum = i;
}
}
line(copy, corners[distNum], corners[minDistNum], Scalar(0, 0, 255), 1, 8, 0);
corners.erase(corners.begin() + distNum);
distNum = minDistNum;
}
imshow(WINDOW_NAME, copy);
waitKey(0);
return 0;
}
```
断点调试发现是corners.erase(corners.begin() + distNum);这一行,当运行到容器corners里某个点时就会报错,但是这点也不是容器corners的末尾点,实在是没看出来为什么错了。
请大神帮我看看,十分感谢!
这是一条镜像帖。来源:北邮人论坛 / cpp / #93675同步于 2016/10/10
该镜像源已超过 30 天没有更新,可能在源站已被删除。
CPP机器人发帖
vector的erase这么写为什么会报错呢?
singingwheat
2016/10/10镜像同步6 回复
订阅后,新回复会通过你的通知中心匿名送达。
6 条回复
不是呀,每次循环里的distNum的值是上一次循环的运算结果
【 在 xiaobing307 的大作中提到: 】
: 是不是因为 int distNum = 0; 要写在循环里面?
报什么错? 错误信息是啥
【 在 singingwheat 的大作中提到: 】
: 不是呀,每次循环里的distNum的值是上一次循环的运算结果
我感觉是因为你遍历这个vector的方法不对,换iterator吧,尤其是你代码里还有erase。std的这些容器的erase都有坑,需要erase(iter++),具体的请自行搜索。
你擦除一个值后,minDistNum已经和原来的位置就对不上了。比如a=[1,2,3,4,5],你先算出minDistNum=3,a[minDistNum]=4。然后你擦除a[1],变成[1,3,4,5],这时候a[minDistNum]=5
distNum = minDistNum;
corners.erase(corners.begin() + distNum);
应该是先获取本次循环要删除的索引吧。。。
按照卤煮的写法,每次删除都是的都是上一次循环获取的索引,但是本次循环的执行删除操作的vector和上次循环已经不一样了