zoukankan      html  css  js  c++  java
  • opencv批处理提取图像的特征

    _________________________________________________________________________________________________________________________________

    批处理(dir/a/s/b)

    例:某文件夹下有a、b、c、d、e、f、g、h、j的图片和一个文件夹JN,里边包括一张图片john.jpg


    我们在该文件夹下的命令行中 输入:dir/b

    b:仅仅显示当前文件夹下文件名称及文件夹名

    a-d:仅仅是显示该文件夹下的文件名称(没有了文件夹的名)

    我们在该文件夹下的命令行中 输入:dir/a-d/b

    S:显示该文件夹下的文件名称和文件夹名,及子文件夹下的文件名称,并显示这些文件的绝对路径

    我们在该文件夹下的命令行中 输入:dir/s/b


    我们在该文件夹下的命令行中 输入:dir/s/a-d/b(因为a-d的作用,文件夹JN没有显示出来)

    我们在该文件夹下的命令行中 输入:dir/s/a-d/b>F:文件夹.txt

    就会在F盘生成一个文件名称为 文件夹 的.txt文件,该文件包括上面的命令行打出的内容。


    —————————————————————————————————————————————————————

    第二步:既然已经生成上述文件 文件夹.txt,然会我们敲代码读取这个 文件夹.txt 就可以。

    <span style="font-family:Microsoft YaHei;font-size:14px;"><span style="font-family:Microsoft YaHei;font-size:14px;"><span style="font-family:Microsoft YaHei;font-size:14px;">#include<iostream>
    #include<fstream>
    #include<string>
    using namespace std;
    int main(int argc,char* argv[])
    {
    	if(argc !=2)
    	{
    		cerr << "Wrong Argument !" <<endl;
    		return -1;
    	}
    	//定义文件流。仅仅能读取
    	ifstream inPutFile(argv[1],ios::in);
    	if(! inPutFile)
    	{
    		cerr << "File Open Erro !" <<endl;
    		return -1;
    	}
    	//读取文件流中的每一行,并赋值给fileName。并在命令行中打印
    	string fileName ;
    	/* 
    	測试读取文件里的每一行
    	*/
    	//行数
    	int number = 0;
    	while (getline(inPutFile,fileName))
    	{
    		number ++;
    		cout<<"第"<< number << "行"<< fileName <<endl;
    	}
        //注意一定要记得关闭文件流
    	inPutFile.close();
    	return 0;
    }</span></span></span>

    我们编译一下:


    我们看一下输出结果:

    好的,这样,说明我们读到了每一行。

    ————————————————————————————————————————————————————

    第三步:配置Opencv,然后,读取显示每一幅图片

    <span style="font-family:Microsoft YaHei;font-size:14px;"><span style="font-family:Microsoft YaHei;font-size:14px;">#include<iostream>
    #include<fstream>
    #include<string>
    using namespace std;
    #include<opencv2imgprocimgproc.hpp>
    #include<opencv2corecore.hpp>
    #include<opencv2highguihighgui.hpp>
    using namespace cv;
    int main(int argc,char* argv[])
    {
    	if(argc !=2)
    	{
    		cerr << "Wrong Argument !" <<endl;
    		return -1;
    	}
    	//定义文件流,仅仅能读取
    	ifstream inPutFile(argv[1],ios::in);
    	if(! inPutFile)
    	{
    		cerr << "File Open Erro !" <<endl;
    		return -1;
    	}
    	//读取文件流中的每一行,并赋值给fileName。读取每一幅图像并显示
    	string fileName ;
    	Mat image;
    	while (getline(inPutFile,fileName))
    	{
    		
    		image = imread(fileName,1);
    		namedWindow(fileName,1);
    		imshow(fileName,image);
    	}
    	waitKey(0);
        //注意一定要记得关闭文件流
    	inPutFile.close();
    	return 0;
    }</span></span>


    结果:

    我们看到我们已经成功把每一幅图像读入到内存中,这样我们就能够求每一幅图像的特征。

    —————————————————————————————————————————————————————

    第四步:我们计算每一幅图像的直方图特征(当然opencv中sift、surf、densesift等,由于我这里的图片大小不一样。所以我用直方图的特征。使得特征向量的长度一样)

    <span style="font-family:Microsoft YaHei;font-size:14px;">#include<iostream>
    #include<fstream>
    #include<string>
    using namespace std;
    
    #include<opencv2imgprocimgproc.hpp>
    #include<opencv2corecore.hpp>
    #include<opencv2highguihighgui.hpp>
    using namespace cv;
    
    //计算二维直方图特征
    Mat hist2d(const Mat& src);
    
    int main(int argc,char* argv[])
    {
    	if(argc !=2)
    	{
    		cerr << "Wrong Argument !" <<endl;
    		return -1;
    	}
    	//定义文件流,仅仅能读取
    	ifstream inPutFile(argv[1],ios::in);
    	if(! inPutFile)
    	{
    		cerr << "File Open Erro !" <<endl;
    		return -1;
    	}
    	//读取文件流中的每一行,并赋值给fileName,读取每一幅图像并显示
    	string fileName ;
    	Mat image;
    	Mat featureHist;
    	Mat featureHists;
    	while (getline(inPutFile,fileName))
    	{
    		
    		image = imread(fileName,1);
    		//计算二维直方图特征
    		featureHist = hist2d(image);
    		//按行存储每一幅图像的二维直方图特征
    		featureHists.push_back(featureHist);
    	}
        //注意一定要记得关闭文件流
    	inPutFile.close();
    	return 0;
    }
    
    Mat hist2d(const Mat& src)
    {
    	Mat hsv;
    
    	//颜色空间的转换 BGR2HSV
    	cvtColor(src,hsv,CV_BGR2HSV);
    
    	//把H通道分为30个bin。把S通道分为32bin
    	int hbins = 30;
    	int sbins = 32;
    	int histSize[] = { hbins , sbins};
    
    	//H的取值范围 0-179
    	float hranges[]= {0,180};
    	//S的取值范围 0-255
    	float sranges [] ={0,256};
    	const float* ranges [] ={hranges,sranges};
    
    	Mat hist2D,histRow,histRowDst;
    	//我们依据图像的第一通道和第二通道,计算二维直方图,并且输出的hist2D为32F
    	int channels [] ={0,1};
    	calcHist(&hsv,1,channels,Mat(),hist2D,2,histSize,ranges,true,false);
    	//把直方图特征按一行来存储
    	histRow=hist2D.reshape(1,1);
    
    	//把直方图归一化
    	normalize(histRow,histRowDst,1,0,NORM_L1);
    
    	return histRowDst;
    }</span>
    这样就把全部的图像的二维直方图特征按行存储在featureHists中。

    当然能够把二维直方图特征换成自己想要用的随意特征。


    —————————————————————————————————————————————————————

    第五步:

    我们全部图像的颜色直方图存储到.xml文件里,

    #include<iostream>
    #include<fstream>
    #include<string>
    using namespace std;
    
    #include<opencv2imgprocimgproc.hpp>
    #include<opencv2corecore.hpp>
    #include<opencv2highguihighgui.hpp>
    using namespace cv;
    
    //计算二维直方图特征
    Mat hist2d(const Mat& src);
    
    int main(int argc,char* argv[])
    {
    	if(argc !=2)
    	{
    		cerr << "Wrong Argument !" <<endl;
    		return -1;
    	}
    	//定义文件流。仅仅能读取
    	ifstream inPutFile(argv[1],ios::in);
    	if(! inPutFile)
    	{
    		cerr << "File Open Erro !" <<endl;
    		return -1;
    	}
    	//读取文件流中的每一行。并赋值给fileName。读取每一幅图像并显示
    	string fileName ;
    	Mat image;
    	Mat featureHist;
    	Mat featureHists;
    	while (getline(inPutFile,fileName))
    	{
    		
    		image = imread(fileName,1);
    		//计算二维直方图特征
    		featureHist = hist2d(image);
    		//按行存储每一幅图像的二维直方图特征
    		featureHists.push_back(featureHist);
    	}
        //注意一定要记得关闭文件流
    	inPutFile.close();
    
    	/*第五步。把图像特征保存到.xml文件里*/
    	FileStorage fs("C:\Users\zhaoyuan001\Desktop\test\dirtest\x64\Debug\da.xml",FileStorage::WRITE);
    	fs<<"featureHists"<<featureHists;
    	fs.release();
    	
    	return 0;
    }
    
    Mat hist2d(const Mat& src)
    {
    	Mat hsv;
    
    	//颜色空间的转换 BGR2HSV
    	cvtColor(src,hsv,CV_BGR2HSV);
    
    	//把H通道分为30个bin,把S通道分为32bin
    	int hbins = 30;
    	int sbins = 32;
    	int histSize[] = { hbins , sbins};
    
    	//H的取值范围 0-179
    	float hranges[]= {0,180};
    	//S的取值范围 0-255
    	float sranges [] ={0,256};
    	const float* ranges [] ={hranges,sranges};
    
    	Mat hist2D,histRow,histRowDst;
    	//我们依据图像的第一通道和第二通道,计算二维直方图,并且输出的hist2D为32F
    	int channels [] ={0,1};
    	calcHist(&hsv,1,channels,Mat(),hist2D,2,histSize,ranges,true,false);
    	//把直方图特征按一行来存储
    	histRow=hist2D.reshape(1,1);
    
    	//把直方图归一化
    	normalize(histRow,histRowDst,1,0,NORM_L1);
    
    	return histRowDst;
    }
    _______________________________________________________________________________________________________________________________

    上面已经批处理提取了图像的特征,那么通常我们再做目标识别、检測时。会给训练数据集,准备类标签。以下,继续对上述程序进行拓展。




  • 相关阅读:
    (转发)storm 入门原理介绍
    shell :将标准输出及标准错误输出写到指定文件
    shell循环(两个日期比较,改变某个特定日期来改变当前比较值)
    MongoDB基本操作
    (转)cenntos 安装mongodb
    通过spark sql 将 hdfs上文件导入到mongodb
    股票实战--线性回归
    Python PIL 的image类和numpy array之间的互换
    根据关键点的脸型的计算
    用反卷积(Deconvnet)可视化理解卷积神经网络还有使用tensorboard
  • 原文地址:https://www.cnblogs.com/zsychanpin/p/7232484.html
Copyright © 2011-2022 走看看