CV_BOOST_IMPL
CvClassifier* cvCreateStumpClassifier( CvMat* trainData, //训练样本的数据,包含图像大小。数量,类别,权重等
int flags, //0表示矩阵的列是训练样本。1表示行是训练样本
CvMat* trainClasses, //表示训练样本的类别矩阵
CvMat* /*typeMask*/,
CvMat* missedMeasurementsMask,
CvMat* compIdx, //特征序列
CvMat* sampleIdx, //训练样本排序后的寻列
CvMat* weights, //训练样本的权重矩阵
CvClassifierTrainParams* trainParams//训练參数
)
{
CvStumpClassifier* stump = NULL;
int m = 0; /* 样本数量number of samples */
int n = 0; /* 特征数量number of components */
uchar* data = NULL;
int cstep = 0; //一个特征(component)在水平方向上的长度,即是水平方向上所占字节数
int sstep = 0; //一个样本(sample)在水平方向上的长度,即是水平方向上所占字节数(这两个參数我看了非常长时间才看出来)
uchar* ydata = NULL;
int ystep = 0;
uchar* idxdata = NULL;
int idxstep = 0;
int l = 0; /* number of indices */
uchar* wdata = NULL;
int wstep = 0; int* idx = NULL;
int i = 0; float sumw = FLT_MAX;
float sumwy = FLT_MAX;
float sumwyy = FLT_MAX; CV_Assert( trainData != NULL );
CV_Assert( CV_MAT_TYPE( trainData->type ) == CV_32FC1 );
CV_Assert( trainClasses != NULL );
CV_Assert( CV_MAT_TYPE( trainClasses->type ) == CV_32FC1 );
CV_Assert( missedMeasurementsMask == NULL );
CV_Assert( compIdx == NULL );
CV_Assert( weights != NULL );
CV_Assert( CV_MAT_TYPE( weights->type ) == CV_32FC1 );
CV_Assert( trainParams != NULL ); data = trainData->data.ptr;
if( CV_IS_ROW_SAMPLE( flags ) )//当traindata训练样本是按行排列,一行表示一个训练样本在不同特征下的特征值
{
cstep = CV_ELEM_SIZE( trainData->type );
sstep = trainData->step;
m = trainData->rows; //行数表示样本数量
n = trainData->cols; //列数表示特征的个数
}
else //当traindata训练样本是按列排列,一列表示一个训练样本在不同特征下的特征值
{
sstep = CV_ELEM_SIZE( trainData->type );
cstep = trainData->step;
m = trainData->cols; //列数表示样本的数量
n = trainData->rows; //行数表示特征的个数
} ydata = trainClasses->data.ptr;
if( trainClasses->rows == 1 )
{
assert( trainClasses->cols == m );
ystep = CV_ELEM_SIZE( trainClasses->type );
}
else
{
assert( trainClasses->rows == m );
ystep = trainClasses->step;
} wdata = weights->data.ptr;
if( weights->rows == 1 )
{
assert( weights->cols == m );
wstep = CV_ELEM_SIZE( weights->type );
}
else
{
assert( weights->rows == m );
wstep = weights->step;
} l = m;
if( sampleIdx != NULL )
{
assert( CV_MAT_TYPE( sampleIdx->type ) == CV_32FC1 ); idxdata = sampleIdx->data.ptr;
if( sampleIdx->rows == 1 )
{
l = sampleIdx->cols;
idxstep = CV_ELEM_SIZE( sampleIdx->type );
}
else
{
l = sampleIdx->rows;
idxstep = sampleIdx->step;
}
assert( l <= m );
} idx = (int*) cvAlloc( l * sizeof( int ) );//为idx分配内存
stump = (CvStumpClassifier*) cvAlloc( sizeof( CvStumpClassifier) );//为stump分配内存 /* START */
memset( (void*) stump, 0, sizeof( CvStumpClassifier ) );//stump内存初始化为零 stump->eval = cvEvalStumpClassifier;
stump->tune = NULL;
stump->save = NULL;
stump->release = cvReleaseStumpClassifier; stump->lerror = FLT_MAX;
stump->rerror = FLT_MAX;
stump->left = 0.0F;
stump->right = 0.0F; /* copy indices */
if( sampleIdx != NULL )
{
for( i = 0; i < l; i++ )
{
idx[i] = (int) *((float*) (idxdata + i*idxstep));
}
}
else
{
for( i = 0; i < l; i++ )
{
idx[i] = i;
}
} for( i = 0; i < n; i++ ) //遍历全部特征
{
CvValArray va; va.data = data + i * ((size_t) cstep);
va.step = sstep;
icvSortIndexedValArray_32s( idx, l, &va );//对数据进行排序
if( findStumpThreshold_32s[(int) ((CvStumpTrainParams*) trainParams)->error]
//该error是计算不纯度的方式,包含四种,各自是:熵不纯度,吉尼不纯度,错分类不纯度,和最小二乘不纯度
( data + i * ((size_t) cstep), sstep,
wdata, wstep, ydata, ystep, (uchar*) idx, sizeof( int ), l,
&(stump->lerror), &(stump->rerror),
&(stump->threshold), &(stump->left), &(stump->right),
&sumw, &sumwy, &sumwyy ) ) //寻找树桩分类器的阈值
{
stump->compidx = i;
}
} /* for each component */ /* END */ cvFree( &idx ); if( ((CvStumpTrainParams*) trainParams)->type == CV_CLASSIFICATION_CLASS )
{
stump->left = 2.0F * (stump->left >= 0.5F) - 1.0F;
stump->right = 2.0F * (stump->right >= 0.5F) - 1.0F;
} return (CvClassifier*) stump;
}

cvCreateStumpClassifier的更多相关文章

  1. opencv源代码之中的一个:cvboost.cpp

    我使用的是opencv2.4.9.安装后.我的cvboost..cpp文件的路径是........\opencv\sources\apps\haartraining\cvboost.cpp.研究源代码 ...

  2. 史上最全opencv源代码解读,opencv源代码具体解读文件夹

    本博原创,如有转载请注明本博网址http://blog.csdn.net/ding977921830/article/details/46799043. opencv源代码主要是基于adaboost算 ...

随机推荐

  1. 关于NotificationListenerService监听时有失败的处理

    关于NotificationListenerService监听时有失败的处理 问题由来 去年进入一家专业做智能穿戴设备的公司,在项目中需要监听系统通知栏变化(主要是IM类app的信息获取到后推送到用户 ...

  2. vue里面使用Velocity.js

    英文文档:http://velocityjs.org/ https://github.com/julianshapiro/velocity 中文手册(教程):http://www.mrfront.co ...

  3. Java中包的介绍

    包的介绍: 未命名包 命名包 可以避免类名重复 为了更好地组织类,Java 提供了包机制,用于区别类名的命名空间. 包的作用 1.把功能相似或相关的类或接口组织在同一个包中,方便类的查找和使用. 2. ...

  4. 打开文件或者uri的方式--------进程启动文件和启动者启动文件

    The  Process class in  System.Diagnostics allows you to launch a new process.For security reasons, t ...

  5. activiti流程跟踪图算法

    流程跟踪图-推导算法 工作中使用activiti实现流程图相关业务,但是上线后遇到问题,偶尔流程图出不来.查阅了一下画流程图的实现,基本上是参见:activiti-流程图颜色变化之一篇. 核心类,参见 ...

  6. Java编程的逻辑 (5) - 小数计算为什么会出错?

    本系列文章经补充和完善,已修订整理成书<Java编程的逻辑>,由机械工业出版社华章分社出版,于2018年1月上市热销,读者好评如潮!各大网店和书店有售,欢迎购买,京东自营链接:http:/ ...

  7. Angular和Vue.js

    Angular和Vue.js Vue.js 是开源的 JavaScript 框架,能够帮助开发者构建出美观的 Web 界面.当和其它网络工具配合使用时,Vue.js 的优秀功能会得到大大加强.如今,已 ...

  8. 【LOJ】#2568. 「APIO2016」烟花表演

    题解 这个听起来很毒瘤的想法写起来却非常休闲,理解起来可能很费劲 例如,我们首先到猜到答案是个下凸包 然后是不是要三分???然而并不是orz 我们通过归纳证明这个下凸包的结论来总结出了一个算法 也就是 ...

  9. 【LOJ】#2082. 「JSOI2016」炸弹攻击 2

    题解 想到n3发现思路有点卡住了 对于每个发射塔把激光塔和敌人按照极角排序,对于一个激光塔,和它转角不超过pi的激光塔中间夹的敌人总和就是答案 记录前缀和,用two-Points扫一下就行 代码 #i ...

  10. VS2010中设置程序以管理员身份运行

    VS2010中设置程序以管理员身份运行 直接项目右键---属性---连接器---清单文件---uac执行级别 选择requireAdministrator 重新编译 即可 这样程序直接运行就拥有管理员 ...