当前位置:   article > 正文

C/C++开发,opencv内置背景减除算法与运动检测

C/C++开发,opencv内置背景减除算法与运动检测

目录

一、c++ opencv 背景减除算法内置算法

1.1 MOG2算法

1.2 KNN算法

二、完整案例实现

2.1 程序代码

2.2 程序编译及输出


一、c++ opencv 背景减除算法内置算法

        背景减除算法的目标是将视频帧中的背景与前景(通常是移动的对象)分离。OpenCV提供MOG2(Gaussian Mixture-based Background/Foreground Segmentation)和KNN(K-Nearest Neighbors)等背景减除算法,他们都派生于BackgroundSubtractor,各派生类需要重写父类的apply函数。

CV_WRAP virtual void apply(InputArray image, OutputArray fgmask, double learningRate=-1) = 0;

这些内置算法,来自video模块的modules\video\include\opencv2\video\background_segm.hpp。

1.1 MOG2算法

        BackgroundSubtractorMOG2是基于高斯混合模型(Gaussian Mixture Model, GMM)的背景减除算法。它适用于处理具有动态背景的场景,如对于缓慢变化的光照条件和动态背景(如摇曳的树叶或水面波纹)也具有一定的鲁棒性。

        apply()函数是BackgroundSubtractorMOG2类的一个重写父类BackgroundSubtractor的成员函数,它接受一个输入帧(frame),并输出一个前景掩模(fgMaskMOG2)。前景掩模是一个灰度图像,其中背景像素接近黑色(值接近0),而前景(移动的对象)像素则更亮(值接近255)。

1.2 KNN算法

        BackgroundSubtractorKNN是基于K近邻(K-Nearest Neighbors, KNN)算法的背景减除器。这种算法对于处理突然的光照变化或复杂的动态背景可能更为有效。

        与BackgroundSubtractorMOG2的示例类似。apply()函数是BackgroundSubtractorKNN类的一个重写父类BackgroundSubtractor的成员函数,它接受一个输入帧(frame),并输出一个前景掩模(fgMaskKNN)。前景掩模是一个灰度图像,其中背景像素接近黑色(值接近0),而前景(移动的对象)像素则更亮(值接近255)。

   BackgroundSubtractorKNN类有几个可以调整的参数,如nframes(用于算法训练的初始帧数)、dist2Threshold(前景检测中的距离阈值)等。这些参数可以通过setNFrames()setDist2Threshold()等成员函数进行设置。

二、完整案例实现

2.1 程序代码

        main.cpp代码,先读取一段视频或打开摄像头,并创建一个BackgroundSubtractorMOG2实例或BackgroundSubtractorKNN实例。然后,在读取视频帧的循环中,使用apply()方法将当前帧与背景模型进行比较,并生成一个前景掩模(fgMask)。这个掩模是一个与输入帧相同大小的灰度图像,其中背景像素接近黑色(值接近0),而前景像素则更亮(值接近255)。

  1. #include <opencv2/opencv.hpp>
  2. #include <vector>
  3. #include <iostream>
  4. int main(int argc, char* argv[])
  5. {
  6. cv::VideoCapture capture; // 视频捕获对象
  7. if(argc< 2){
  8. capture.open(0); //0是摄像头的索引
  9. }else{
  10. // 加载视频
  11. capture.open(argv[1]); //如果是视频文件,则传入文件路径
  12. }
  13. // cv::VideoCapture capture(0); // 0是摄像头的索引,如果是视频文件,则传入文件路径
  14. if (!capture.isOpened()) {
  15. std::cerr << "Error opening video stream or file" << std::endl;
  16. return -1;
  17. }
  18. // 创建背景减除器对象
  19. cv::Ptr<cv::BackgroundSubtractorMOG2> pBackSub = cv::createBackgroundSubtractorMOG2();
  20. // cv::Ptr<cv::BackgroundSubtractorKNN> pBackSub = cv::createBackgroundSubtractorKNN();
  21. cv::Mat frame, fgMask;
  22. while (capture.read(frame)) {
  23. if (frame.empty())
  24. break;
  25. // 应用背景减除
  26. pBackSub->apply(frame, fgMask);
  27. // 可选:进行一些形态学操作来去除噪声
  28. cv::Mat kernel = cv::getStructuringElement(cv::MORPH_ELLIPSE, cv::Size(3, 3));
  29. morphologyEx(fgMask, fgMask, cv::MORPH_OPEN, kernel);
  30. // 显示结果
  31. imshow("Frame", frame);
  32. imshow("FG Mask", fgMask);
  33. // 对检测图像进行判断
  34. char c = (char) cv::waitKey(30);
  35. if (c == 27) break; // 按ESC退出
  36. }
  37. capture.release();
  38. cv::destroyAllWindows();
  39. return 0;
  40. }
2.2 程序编译及输出

        本文是采用win系统下,opencv采用MinGW编译的静态库(C/C++开发,win下OpenCV+MinGW编译环境搭建_opencv mingw-CSDN博客),建立makefile:

  1. #/bin/sh
  2. #win32
  3. CX= g++ -DWIN32
  4. #linux
  5. #CX= g++ -Dlinux
  6. BIN := ./
  7. TARGET := Motion_detection.exe
  8. FLAGS := -std=c++11 -static
  9. SRCDIR := ./
  10. #INCLUDES
  11. INCLUDEDIR := -I"../../opencv_MinGW/include" -I"./"
  12. #-I"$(SRCDIR)"
  13. staticDir := ../../opencv_MinGW/x64/mingw/staticlib/
  14. #LIBDIR := $(staticDir)/libopencv_world460.a\
  15. # $(staticDir)/libade.a \
  16. # $(staticDir)/libIlmImf.a \
  17. # $(staticDir)/libquirc.a \
  18. # $(staticDir)/libzlib.a \
  19. # $(wildcard $(staticDir)/liblib*.a) \
  20. # -lgdi32 -lComDlg32 -lOleAut32 -lOle32 -luuid
  21. #opencv_world放弃前,然后是opencv依赖的第三方库,后面的库是MinGW编译工具的库
  22. LIBDIR := -L $(staticDir) -lopencv_world460 -lade -lIlmImf -lquirc -lzlib \
  23. -llibjpeg-turbo -llibopenjp2 -llibpng -llibprotobuf -llibtiff -llibwebp \
  24. -lgdi32 -lComDlg32 -lOleAut32 -lOle32 -luuid
  25. source := $(wildcard $(SRCDIR)/*.cpp)
  26. $(TARGET) :
  27. $(CX) $(FLAGS) $(INCLUDEDIR) $(source) -o $(BIN)/$(TARGET) $(LIBDIR)
  28. clean:
  29. rm $(BIN)/$(TARGET)

编译如下:

程序运行输出如下,本测试没有指定视频图像,采用笔记本的摄像头抓取视频:    

PS:读者可以调整参数、图像光影效果等验证测试BackgroundSubtractorKNN方法。 

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/weixin_40725706/article/detail/983811
推荐阅读
相关标签
  

闽ICP备14008679号