高斯分布与背景建模的关系:图像中每一个像素点的颜色值作为一个随机过程X,并假设该点的像素值出现的概率服从高斯分布。令I(x,y,t)表示像素点(x,y,t)在t时刻的像素值,则有:

其中分别为t时刻该像素高斯分布的期望值和标准差。

算法流程:

1.用第一帧图像数据初始化背景模型,其中std_init通常设置为20。

2.检测前景与背景像素。

背景像素检测公式:

前景像素检测公式:

3.对背景值进行更新,更新公式如下:

4.返回到2直至停止。

算法实现代码(vc6.0+opencv1.0):

// singleGaussian.cpp : Defines the entry point for the console application.

#include "stdafx.h"
#include <highgui.h>
#include <cv.h>
#include <math.h>
#include <cxcore.h>

int main(int argc, char* argv[])
{
//新建窗口
    cvNamedWindow("origin", CV_WINDOW_AUTOSIZE);
    cvNamedWindow("background", CV_WINDOW_AUTOSIZE);
    cvNamedWindow("foreground", CV_WINDOW_AUTOSIZE);

double alpha = 0.05;    //背景建模alpha值
    double std_init = 20;    //初始标准差
    double var_init = std_init * std_init;    //初始方差    
    double lamda = 2.5 * 1.2;    //背景更新参数

//视频文件
    CvCapture *capture = NULL;
    //读取视频文件
    if (argc == 1)
    {
        //从摄像头读入
        capture = cvCreateCameraCapture(0);
    }
    else if (argc == 2)
    {
        //从文件读入
        capture = cvCreateFileCapture(argv[1]);
    }
    else
    {
        //读入错误
        printf("input error\n");
        return -1;
    }

IplImage *frame = NULL;        //原始图像
    IplImage *frame_u = NULL;    //期望图像
    IplImage *frame_d = NULL;    //前景图像
    IplImage *frame_var = NULL;    //方差图像
    IplImage *frame_std = NULL;    //标准差

CvScalar pixel = {0};        //像素原始值
    CvScalar pixel_u = {0};        //像素期望
    CvScalar pixel_d = {0};        //像素前景
    CvScalar pixel_var = {0};    //像素方差
    CvScalar pixel_std = {0};    //像素标准差

//初始化frame_u, frame_var, frame_std
    frame = cvQueryFrame(capture);
    frame_u = cvCreateImage(cvSize(frame->width, frame->height), IPL_DEPTH_8U, 3);
    frame_d = cvCreateImage(cvSize(frame->width, frame->height), IPL_DEPTH_8U, 3);
    frame_var = cvCreateImage(cvSize(frame->width, frame->height), IPL_DEPTH_8U, 3);
    frame_std = cvCreateImage(cvSize(frame->width, frame->height), IPL_DEPTH_8U, 3);

for (int y = 0; y < frame->height; ++y)
    {
        for (int x = 0; x < frame->width; ++x)
        {
            pixel = cvGet2D(frame, y, x);
            pixel_u.val[0] = pixel.val[0];
            pixel_u.val[1] = pixel.val[1];
            pixel_u.val[2] = pixel.val[2];

pixel_d.val[0] = 0;
            pixel_d.val[1] = 0;
            pixel_d.val[2] = 0;

pixel_std.val[0] = std_init;
            pixel_std.val[1] = std_init;
            pixel_std.val[2] = std_init;

pixel_var.val[0] = var_init;
            pixel_var.val[1] = var_init;
            pixel_var.val[2] = var_init;

cvSet2D(frame_u, y, x, pixel_u);
            cvSet2D(frame_d, y, x, pixel_d);
            cvSet2D(frame_var, y, x, pixel_var);
            cvSet2D(frame_std, y, x, pixel_std);
        }
    }
    while (cvWaitKey(33) != 27)        //按ESC键退出, 帧率33ms
    {
        frame = cvQueryFrame(capture);
        //视频结束退出
        if (!frame)
        {
            break;
        }
        //单高斯背景更新
        for (int y = 0; y < frame->height; ++y)
        {
            for (int x = 0; x < frame->width; ++x)
            {
                pixel = cvGet2D(frame, y, x);
                pixel_u = cvGet2D(frame_u, y, x);
                pixel_d = cvGet2D(frame_d, y, x);
                pixel_std = cvGet2D(frame_std, y, x);
                pixel_var = cvGet2D(frame_var, y, x);

//|I-u| < lamda*std 时认为是背景, 进行更新
                if (fabs(pixel.val[0] - pixel_u.val[0]) < lamda * pixel_std.val[0] &&
                    fabs(pixel.val[1] - pixel_u.val[1]) < lamda * pixel_std.val[1] &&
                    fabs(pixel.val[2] - pixel_u.val[2]) < lamda * pixel_std.val[2])
                {
                    //更新期望 u = (1-alpha)*u + alpha*I
                    pixel_u.val[0] = (1 - alpha) * pixel_u.val[0] + alpha * pixel.val[0];
                    pixel_u.val[1] = (1 - alpha) * pixel_u.val[1] + alpha * pixel.val[1];
                    pixel_u.val[2] = (1 - alpha) * pixel_u.val[2] + alpha * pixel.val[2];

//更新方差 var = (1-alpha)*var + alpha*(I-u)^2
                    pixel_var.val[0] = (1 - alpha) * pixel_var.val[0] +
                                    (pixel.val[0] - pixel_u.val[0]) * (pixel.val[0] - pixel_u.val[0]);
                    pixel_var.val[1] = (1 - alpha) * pixel_var.val[1] +
                                    (pixel.val[1] - pixel_u.val[1]) * (pixel.val[1] - pixel_u.val[1]);
                    pixel_var.val[2] = (1 - alpha) * pixel_var.val[2] +
                                    (pixel.val[2] - pixel_u.val[2]) * (pixel.val[2] - pixel_u.val[2]);

//更新标准差
                    pixel_std.val[0] = sqrt(pixel_var.val[0]);
                    pixel_std.val[1] = sqrt(pixel_var.val[1]);
                    pixel_std.val[2] = sqrt(pixel_var.val[2]);

//写入矩阵
                    cvSet2D(frame_u, y, x, pixel_u);
                    cvSet2D(frame_var, y, x, pixel_var);
                    cvSet2D(frame_std, y, x, pixel_std);
                }
                else
                {
                    pixel_d.val[0] = pixel.val[0] - pixel_u.val[0];
                    pixel_d.val[1] = pixel.val[1] - pixel_u.val[1];
                    pixel_d.val[2] = pixel.val[2] - pixel_u.val[2];
                    cvSet2D(frame_d, y, x, pixel_d);
               }
            }
        }

//显示结果
        frame_u->origin = 1;
        frame_d->origin = 1;
        cvShowImage("origin", frame);
        cvShowImage("background", frame_u);
        cvShowImage("foreground", frame_d);
    }

//释放内存
    cvReleaseCapture(&capture);
    cvReleaseImage(&frame);
    cvReleaseImage(&frame_u);
    cvReleaseImage(&frame_var);
    cvReleaseImage(&frame_std);
    cvDestroyWindow("origin");
    cvDestroyWindow("background");
    cvDestroyWindow("foreground");

return 0;
}

完善补充:

对于单高斯模型实现必须进行背景减除与阴影消除的处理,实用的模型还需要很多改进!此文仅供初学者研究。

参考链接:

http://underthehood.blog.51cto.com/2531780/484191

背景建模之单高斯实现相关推荐

  1. 高斯背景建模 matlab,高斯背景建模整理 – 要饭的

    OpenCV 中高斯背景建模相关论文 BackgroundSubtractorMOG: Paper : An Improved Adaptive Background Mixture Model fo ...

  2. 运动目标检测_混合高斯背景建模

    1.混合高斯背景建模理论 混合高斯背景建模是基于像素样本统计信息的背景表示方法,利用像素在较长时间内大量样本值的概率密度等统计信息(如模式数量.每个模式的均值和标准差)表示背景,然后使用统计差分(如3 ...

  3. 运动目标检测混合高斯背景建模

    1.混合高斯背景建模理论 混合高斯背景建模是基于像素样本统计信息的背景表示方法,利用像素在较长时间内大量样本值的概率密度等统计信息(如模式数量.每个模式的均值和标准差)表示背景,然后使用统计差分(如3 ...

  4. 基于高斯核密度估计的背景建模和改进的五帧帧差法相融合的运动目标检测算法

    上篇文章所指定的是对一个不包含动态背景的监控视频进行前景提取,用基于改进的五帧帧差和混合高斯模型相融合的前景提取算法是可以很好实现前景提取的.但本文中要求在包含动态背景的监控视频提取前景目标,虽然上篇 ...

  5. 背景建模方法论文总结

    文章名称:Real-tine tracking of the human body 年份:1997 作者:Christopher Richard Wren 算法名称:单高斯背景建模 简单描述: 将每个 ...

  6. 背景建模方法《python图像处理篇》

    引言:在图像处理中,运动检测占据了大部分内容,因为现实生活还是动态更新的,今天要说的是两种传统的背景建模方法,高斯混合模型和VIBE算法(Visual Background Extractor),这两 ...

  7. 运动目标检测_单高斯背景建模

    1.运动目标背景建模 背景建模也称为背景估计,其主要目的是根据当前的背景估计,把对序列图像的运动目标检测问题转化为一个二分类问题,将所有像素划分为背景和运动前景两类,进而对分类结果进行后处理,得到最终 ...

  8. 运动目标检测单高斯背景建模

    1.运动目标背景建模 背景建模也称为背景估计,其主要目的是根据当前的背景估计,把对序列图像的运动目标检测问题转化为一个二分类问题,将所有像素划分为背景和运动前景两类,进而对分类结果进行后处理,得到最终 ...

  9. 【图像处理基础知识】-混合高斯背景建模

    0.高斯模糊原理 转载地址:https://www.cnblogs.com/herenzhiming/articles/5276106.html --------------------------- ...

最新文章

  1. 利用 FastCoding 将对象进行本地持久化
  2. 【oracle】sqlnet.ora 访问控制策略
  3. 关于svn不能cleanup的问题
  4. 移动语义-右值引用-完美转发-万字长文让你一探究竟
  5. mysql设计与实现_mysql设计与开发
  6. C#中的Dictionary字典类介绍(转载)
  7. 95-230-020-源码-WordCount走读-获取StreamGraph的过程
  8. 【数据清洗】异常点的理解与处理方法(1)
  9. JavaWeb——response与request
  10. 832计算机专业基础,2019年考试科目832计算机组成原理与数据结构.doc
  11. Mac上安装homebrew(类似于Linux上的apt-get)
  12. 用matlab解根3乘根2,第六章 信号与系统v1.ppt
  13. linux内存源码分析 - 伙伴系统(释放页框)
  14. Struts框架面试题
  15. Ubuntu安装gcc 以及g++
  16. 对120年的奥运数据进行了可视化分析
  17. RVM怎么下载和管理ruby版本 - 猿码设计师 ruby rvm
  18. 学习笔记 计算机组成原理_名词解释
  19. python 计算快递费
  20. Deen Smart隐私政策

热门文章

  1. PERL 语言中的q,qw,qr,qx,qq......符号用法总结
  2. leetcode算法题--最小的k个数
  3. leetcode算法题--二叉树的最近公共祖先
  4. python批量读取grib_windows python读取grib2数据
  5. Could not load type 'System.Web.Mvc.ViewPagedynamic' in asp.net mvc2 after publishing the website
  6. Linux中java项目环境部署,简单记录一下
  7. 统计的一个小题目python实现
  8. Android中Intent的显示和隐式使用
  9. Coin Slider
  10. 【线段树】【FeyatCup】——2.法法塔的奖励