opencv_createsamples的源码解析

转载自https://blog.csdn.net/xbcReal/article/details/77644956

opencv_createsamples用到了以下几个源码文件,分别是/home/xbc/opencv-2.4.13/apps/haartraining/createsamples.cpp以及/home/xbc/opencv-2.4.13/apps/haartraining/cvsamples.cpp,其中主函数在第一个文件之中。 

createsamples.cpp的源码如下:

#include <cstdio>
#include <cstring>
#include <cstdlib>
#include <cmath>
#include <ctime>
#include <memory>

using namespace std;

#include "cvhaartraining.h"
#include "ioutput.h"

int main( int argc, char* argv[] )
{
    int i = 0;
    char* nullname   = (char*)"(NULL)";
    char* vecname    = NULL; /* .vec file name */
    char* infoname   = NULL; /* file name with marked up image descriptions */
    char* imagename  = NULL; /* single sample image */
    char* bgfilename = NULL; /* background */
    int num = 1000;
    int bgcolor = 0;
    int bgthreshold = 80;
    int invert = 0;
    int maxintensitydev = 40;
    double maxxangle = 1.1;
    double maxyangle = 1.1;
    double maxzangle = 0.5;
    bool showsamples = false;
    /* the samples are adjusted to this scale in the sample preview window */
    double scale = 4.0;
    int width  = 24;
    int height = 24;
    bool pngoutput = false; /* whether to make the samples in png or in jpg*/

    srand((unsigned int)time(0));
    //解析命令行参数的代码
    if( argc == 1 )
    {
        printf( "Usage: %s\n  [-info <collection_file_name>]\n"
                "  [-img <image_file_name>]\n"
                "  [-vec <vec_file_name>]\n"
                "  [-bg <background_file_name>]\n  [-num <number_of_samples = %d>]\n"
                "  [-bgcolor <background_color = %d>]\n"
                "  [-inv] [-randinv] [-bgthresh <background_color_threshold = %d>]\n"
                "  [-maxidev <max_intensity_deviation = %d>]\n"
                "  [-maxxangle <max_x_rotation_angle = %f>]\n"
                "  [-maxyangle <max_y_rotation_angle = %f>]\n"
                "  [-maxzangle <max_z_rotation_angle = %f>]\n"
                "  [-show [<scale = %f>]]\n"
                "  [-w <sample_width = %d>]\n  [-h <sample_height = %d>]\n"
                "  [-pngoutput]",
                argv[0], num, bgcolor, bgthreshold, maxintensitydev,
                maxxangle, maxyangle, maxzangle, scale, width, height );

        return 0;
    }

    for( i = 1; i < argc; ++i )
    {
        if( !strcmp( argv[i], "-info" ) )
        {
            infoname = argv[++i];
        }
        else if( !strcmp( argv[i], "-img" ) )
        {
            imagename = argv[++i];
        }
        else if( !strcmp( argv[i], "-vec" ) )
        {
            vecname = argv[++i];
        }
        else if( !strcmp( argv[i], "-bg" ) )
        {
            bgfilename = argv[++i];
        }
        else if( !strcmp( argv[i], "-num" ) )
        {
            num = atoi( argv[++i] );
        }
        else if( !strcmp( argv[i], "-bgcolor" ) )
        {
            bgcolor = atoi( argv[++i] );
        }
        else if( !strcmp( argv[i], "-bgthresh" ) )
        {
            bgthreshold = atoi( argv[++i] );
        }
        else if( !strcmp( argv[i], "-inv" ) )
        {
            invert = 1;
        }
        else if( !strcmp( argv[i], "-randinv" ) )
        {
            invert = CV_RANDOM_INVERT;
        }
        else if( !strcmp( argv[i], "-maxidev" ) )
        {
            maxintensitydev = atoi( argv[++i] );
        }
        else if( !strcmp( argv[i], "-maxxangle" ) )
        {
            maxxangle = atof( argv[++i] );
        }
        else if( !strcmp( argv[i], "-maxyangle" ) )
        {
            maxyangle = atof( argv[++i] );
        }
        else if( !strcmp( argv[i], "-maxzangle" ) )
        {
            maxzangle = atof( argv[++i] );
        }
        else if( !strcmp( argv[i], "-show" ) )
        {
            showsamples = true;
            if( i+1 < argc && strlen( argv[i+1] ) > 0 && argv[i+1][0] != '-' )
            {
                double d;
                d = strtod( argv[i+1], 0 );
                if( d != -HUGE_VAL && d != HUGE_VAL && d > 0 ) scale = d;
                ++i;
            }
        }
        else if( !strcmp( argv[i], "-w" ) )
        {
            width = atoi( argv[++i] );
        }
        else if( !strcmp( argv[i], "-h" ) )
        {
            height = atoi( argv[++i] );
        }
        else if( !strcmp( argv[i], "-pngoutput" ) )
        {
            pngoutput = true;
        }
    }

    printf( "Info file name: %s\n", ((infoname == NULL) ?   nullname : infoname ) );
    printf( "Img file name: %s\n",  ((imagename == NULL) ?  nullname : imagename ) );
    printf( "Vec file name: %s\n",  ((vecname == NULL) ?    nullname : vecname ) );
    printf( "BG  file name: %s\n",  ((bgfilename == NULL) ? nullname : bgfilename ) );
    printf( "Num: %d\n", num );
    printf( "BG color: %d\n", bgcolor );
    printf( "BG threshold: %d\n", bgthreshold );
    printf( "Invert: %s\n", (invert == CV_RANDOM_INVERT) ? "RANDOM"
                                : ( (invert) ? "TRUE" : "FALSE" ) );
    printf( "Max intensity deviation: %d\n", maxintensitydev );
    printf( "Max x angle: %g\n", maxxangle );
    printf( "Max y angle: %g\n", maxyangle );
    printf( "Max z angle: %g\n", maxzangle );
    printf( "Show samples: %s\n", (showsamples) ? "TRUE" : "FALSE" );
    if( showsamples )
    {
        printf( "Scale applied to display : %g\n", scale );
    }
    if( !pngoutput)
    {
        printf( "Original image will be scaled to:\n");
        printf( "\tWidth: $backgroundWidth / %d\n", width );
        printf( "\tHeight: $backgroundHeight / %d\n", height );
    }
    //解析命令行参数的代码到此结束
    /* determine action */
    //根据输入的是描述待检测物体的info文件还是一张图像的名字文件执行不同的操作,一般我们在网上找到的教程多是根据info.dat或者info.txt来创建samples的,创建samples的例子可以参考:
    http://www.cnblogs.com/easymind223/archive/2012/07/03/2574826.html,因此我们这里只查看下面的if语句中的“else if( infoname && vecname )”
    //我们不关注这部分代码
    if( imagename && vecname )
    {
        printf( "Create training samples from single image applying distortions...\n" );

        cvCreateTrainingSamples( vecname, imagename, bgcolor, bgthreshold, bgfilename,
                                 num, invert, maxintensitydev,
                                 maxxangle, maxyangle, maxzangle,
                                 showsamples, width, height );

        printf( "Done\n" );
    }
    //我们不关注这部分代码
    else if( imagename && bgfilename && infoname)
    {
        printf( "Create data set from single image applying distortions...\n"
                "Output format: %s\n",
                (( pngoutput ) ? "PNG" : "JPG") );

        std::auto_ptr<DatasetGenerator> creator;
        if( pngoutput )
        {
            creator = std::auto_ptr<DatasetGenerator>( new PngDatasetGenerator( infoname ) );
        }
        else
        {
            creator = std::auto_ptr<DatasetGenerator>( new JpgDatasetGenerator( infoname ) );
        }
        creator->create( imagename, bgcolor, bgthreshold, bgfilename, num,
                        invert, maxintensitydev, maxxangle, maxyangle, maxzangle,
                        showsamples, width, height );

        printf( "Done\n" );
    }
    //我们关注这部分代码,因为这里使用了info文件创建.vec文件,是我们常见的方法
    else if( infoname && vecname )
    {
        int total;

        printf( "Create training samples from images collection...\n" );
    //在这里真正地创建了.vec文件
        total = cvCreateTrainingSamplesFromInfo( infoname, vecname, num, showsamples,
                                                 width, height );

        printf( "Done. Created %d samples\n", total );
    }
    //我们不关注这部分代码
    else if( vecname )
    {
        printf( "View samples from vec file (press ESC to exit)...\n" );

        cvShowVecSamples( vecname, width, height, scale );

        printf( "Done\n" );
    }
    else
    {
        printf( "Nothing to do\n" );
    }

    return 0;
}
  • 还有两个辅助的函数:
void icvWriteVecHeader( FILE* file, int count, int width, int height )
{
    int vecsize;
    short tmp;

    /* number of samples */
    fwrite( &count, sizeof( count ), 1, file );
    /* vector size */
    vecsize = width * height;
    fwrite( &vecsize, sizeof( vecsize ), 1, file );
    /* min/max values */
    tmp = 0;
    fwrite( &tmp, sizeof( tmp ), 1, file );
    fwrite( &tmp, sizeof( tmp ), 1, file );
}

void icvWriteVecSample( FILE* file, CvArr* sample )
{
    CvMat* mat, stub;
    int r, c;
    short tmp;
    uchar chartmp;

    mat = cvGetMat( sample, &stub );
    chartmp = 0;
    fwrite( &chartmp, sizeof( chartmp ), 1, file );
    for( r = 0; r < mat->rows; r++ )
    {
        for( c = 0; c < mat->cols; c++ )
        {
            tmp = (short) (CV_MAT_ELEM( *mat, uchar, r, c ));
            fwrite( &tmp, sizeof( tmp ), 1, file );
        }
    }
}

至此opencv_createsamples的源码文件就解析完毕了,读完源码还意识到对于使用info文件创建.vec文件的方法来说,-bg这个参数根本用不到,之前我在自己利用info文件创建.vec文件的时候还有将这个-bg的参数填为存储负样本名字的文件名,事实上这是多余的。

转载至博客: https://blog.csdn.net/xbcReal/article/details/77644956    感谢博主贡献

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值