【练习8.1】查找轮廓、寻找关键点cvFindDominantPoints、访问序列中的元素
2015-05-16 17:48
716 查看
题目要求 | 程序代码 | 结果图片 | 要言妙道 | 借鉴参考 |
查找轮廓并使用 cvFindDominantPoints 寻找关键点,看缩放图像和旋转图像会否影响到IPAN算法的结果
程序代码:
// OpenCVExerciseTesting.cpp : 定义控制台应用程序的入口点。 // //D:\\Work\\Work_Programming\\Source\\Image\\lena.jpg #include "stdafx.h" #include<string> #include <cv.h> #include <highgui.h> #include <iostream> #include <opencv2/legacy/legacy.hpp> //#pragma comment(lib, "opencv_legacy2411.lib") using namespace cv; using namespace std; //函数声明-->--->-->--->-->--->-->--->// string itos(int i) // 将int 转换成string { stringstream s; s << i; return s.str(); } //<--<--<--<--<--<--<--<--<--函数声明// int _tmain(int argc, _TCHAR* argv[]) { IplImage * image_Resource; string window_name; string image_full_name[8]; image_full_name[0] = "D:\\Work\\Work_Programming\\Source\\Image\\OpenCVExerciseImage\\第8章\\bracket_mask.jpg"; image_full_name[1] = "D:\\Work\\Work_Programming\\Source\\Image\\OpenCVExerciseImage\\第8章\\bracket_mask_80%.jpg"; image_full_name[2] = "D:\\Work\\Work_Programming\\Source\\Image\\OpenCVExerciseImage\\第8章\\bracket_mask_120%.jpg"; image_full_name[3] = "D:\\Work\\Work_Programming\\Source\\Image\\OpenCVExerciseImage\\第8章\\bracket_mask_15度.jpg"; image_full_name[4] = "D:\\Work\\Work_Programming\\Source\\Image\\OpenCVExerciseImage\\第8章\\bracket_mask_-15度60%.jpg"; image_full_name[5] = "D:\\Work\\Work_Programming\\Source\\Image\\OpenCVExerciseImage\\第8章\\bracket_mask_-15度.jpg"; image_full_name[6] = "D:\\Work\\Work_Programming\\Source\\Image\\OpenCVExerciseImage\\第8章\\bracket_mask_-75度.jpg"; image_full_name[7] = "D:\\Work\\Work_Programming\\Source\\Image\\OpenCVExerciseImage\\第8章\\bracket_mask_105度.jpg"; for (int file_name_i = 0; file_name_i < 8; ++file_name_i) { image_Resource = cvLoadImage(image_full_name[file_name_i].c_str(), CV_LOAD_IMAGE_GRAYSCALE); assert(image_Resource); IplImage * image_binary = cvCloneImage(image_Resource); cvZero(image_binary); //二值化图像 double thread_ReturnValue;; thread_ReturnValue = cvThreshold(image_Resource, image_binary, 200, 255, CV_THRESH_BINARY); //window_name = "二值图像"; //window_name = window_name + itos(file_name_i); //cvNamedWindow(window_name.data(), CV_WINDOW_AUTOSIZE); //cvShowImage(window_name.data(), image_binary); //查找轮廓 CvMemStorage * storage = cvCreateMemStorage(); CvSeq * first_contour; int contourNum; contourNum = cvFindContours(image_binary, storage, &first_contour, sizeof(CvContour), CV_RETR_EXTERNAL); //显示原始二值图像轮廓 IplImage * image_contours = cvCreateImage(cvGetSize(image_binary), IPL_DEPTH_8U, 1); cvZero(image_contours); cvDrawContours(image_contours, first_contour, cvScalar(255), cvScalar(125), 0); window_name = "原始二值图轮廓图像"; window_name = window_name + itos(file_name_i); cvNamedWindow(window_name.data(), CV_WINDOW_AUTOSIZE); cvShowImage(window_name.data(), image_contours); //寻找关键点 CvSeq *dominant = NULL; CvMemStorage *storate_dominant = cvCreateMemStorage(); dominant = cvFindDominantPoints(first_contour, storate_dominant); IplImage *image_dominant = cvCreateImage(cvGetSize(image_contours), IPL_DEPTH_8U, 1); cvZero(image_dominant); for (int i = 0; i < dominant->total; ++i) { //cvFindDominantPoints返回的只是索引,所以,用下面两行代码无法画出关键点 //CvPoint *point = (CvPoint*)cvGetSeqElem(dominant, i); // cvCircle(image_dominant, *point, 5, cvScalar(255)); int idx = *(int *)cvGetSeqElem(dominant, i); CvPoint pt = *(CvPoint *)cvGetSeqElem(first_contour, idx); cvDrawCircle(image_dominant, pt, 1, cvScalar(255)); } window_name = "寻找到的关键点"; window_name = window_name + itos(file_name_i); cvNamedWindow(window_name.c_str(), CV_WINDOW_AUTOSIZE); cvShowImage(window_name.c_str(), image_dominant); cvReleaseImage(&image_binary); cvReleaseImage(&image_contours); cvReleaseImage(&image_dominant); } cvWaitKey(0); cvReleaseImage(&image_Resource); cvDestroyAllWindows(); return 0; }
结果图片:
①:cvFindContours的输入图像必须是8位单通道图像,并且应该被转化为二值的;注意:cvFindContours运行时,这个图像会被直接涂改,所以,注意使用副本。
②cvFindContours的first_contours参数时一个指向CvSeq* 的指针,只需传一个指针即可,无需动手分配内存,也不要分配和释放,cvFindContours函数会自动设置它的值 CvSeq* firstContour = NULL; cvFindContours( …, &firstContour, … );
③ 注意 cvFindDominantPoints 返回的只是关键点在轮廓中的索引,而不是点的序列,如果需要得到关键点的坐标,还需要将该索引传入到 cvGetSeqElem 才可以
④从测试的结果看,缩放会影响IPAN算法返回的结果,特别是当图像的轮廓线不是水平或垂直的时候,旋转也会影响。
借鉴参考:
相关文章推荐
- opnecv扫描轮廓寻找关键点cvFindDominantPoints的运用
- 【练习8.6】使用不同参数值观察cvFindDominantPoints寻找关键点的效果
- openCV 学习笔记 cvFindDominantPoints找关键点
- opencv查找轮廓---cvFindContours && cvDrawCountours 用法及例子
- 【OpenCV3】图像轮廓查找与绘制——cv::findContours()与cv::drawContours()详解
- opencv查找轮廓---cvFindContours && cvDrawCountours 用法及例子
- OpenCV笔记10:用cvFindContours查找图像轮廓并显示
- 图像轮廓查找与绘制——cv::findContours()与cv::drawContours()详解
- OpenCV通过cvFindContours与cvDrawCountours函数查找轮廓
- opencv查找轮廓---cvFindContours && cvDrawCountours 用法及例子
- Find Min In Rotated Sorted Array,寻找反转序列中最小的元素。
- opencv查找轮廓---cvFindContours && cvDrawCountours 用法及例子
- opencv序列结构CvSeq和轮廓提取cvFindContours的简单运用
- OpenCV通过cvFindContours与cvDrawCountours函数查找轮廓
- opencv cvFindContours 查找轮廓 cvDrawCountours 用法及例子
- opencv查找轮廓---cvFindContours && cvDrawCountours 用法及例子
- opencv之查找轮廓---cvFindContours && cvDrawCountours 用法及例子
- OpenCV通过cvFindContours与cvDrawCountours函数查找轮廓
- opencv查找轮廓---cvFindContours && cvDrawCountours 用法及例子
- Find Mode in Binary Search Tree:带重复元素的搜索二叉树Morris遍历查找频率最大的元素