图像检索:一维直方图+欧几里得距离+flann+KNN

在F盘生成了一个文件名称为“文件夹”的文本文件。


第一步:批处理提取图像的一维颜色直方图,并保存到.xml中的featureHists

第一个參数:图像的路径

第二个參数:保存的.xml

#include<iostream>
#include<fstream>
#include<string>
using namespace std;

#include<opencv2imgprocimgproc.hpp>
#include<opencv2corecore.hpp>
#include<opencv2highguihighgui.hpp>
using namespace cv;

//计算一维直方图特征
Mat hist1d(const Mat& src);

int main(int argc,char* argv[])
{
    if(argc !=3)
    {
        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 = hist1d(image);
        //按行存储每一幅图像的一维直方图特征
        featureHists.push_back(featureHist);
    }
    //注意一定要记得关闭文件流
    inPutFile.close();

    /*第五步。把图像特征保存到.xml文件里*/
    FileStorage fs(argv[2],FileStorage::WRITE);
    fs<<"featureHists"<<featureHists;
    fs.release();
    
    return 0;
}

Mat hist1d(const Mat& src)
{
    Mat hsv;

    //颜色空间的转换 BGR2HSV
    cvtColor(src,hsv,CV_BGR2HSV);

    //把H通道分为60个bin
    int hbins = 60;
    int histSize[] = { hbins };

    //H的取值范围 0-179
    float hranges[]= {0,180};
    const float* ranges [] ={hranges};

    Mat hist1D,histRow,histRowDst;
    //我们依据图像的第一通道。计算一维直方图,并且输出的hist1D为32F
    int channels [] ={0};
    calcHist(&hsv,1,channels,Mat(),hist1D,1,histSize,ranges,true,false);
    //把直方图特征按一行来存储
    histRow=hist1D.reshape(1,1);

    //把直方图归一化
    normalize(histRow,histRowDst,1,0,NORM_L1);

    return histRowDst;
}

编译完毕后,进入命令行

然后,在F盘出现了一个features的.xml文件。里边存储了上述图像一维直方图特征。

—————————————————————————————————————————————————————————————————————————————
第二步:提取色卡的一维颜色直方图

#include<iostream>
#include<string>
using namespace std;

#include<opencv2corecore.hpp>
#include<opencv2highguihighgui.hpp>
#include<opencv2imgprocimgproc.hpp>
using namespace cv;


int main(int argc,char* argv[])
{
	Mat src = imread(argv[1],1);
	if(! src.data)
	{
		cout <<"No Image" << endl;
		return -1;
	}
		
	Mat hsv;
	//颜色空间的转换BGR2HSV
	cvtColor(src,hsv,CV_BGR2HSV);

	//把H通道分为60个bin
	int hbins = 60;
	int histSize[] = { hbins };

	//H的取值范围 0-179
	float hranges[]= {0,180};
	
	const float* ranges [] ={hranges};
	Mat hist1D,histRow,histRowDst;
	//我们依据图像的第一通道,计算一维直方图,并且输出的hist1D为32F
	int channels [] ={0};
	calcHist(&hsv,1,channels,Mat(),hist1D,1,histSize,ranges,true,false);
	//把直方图特征按一行来存储
	histRow=hist1D.reshape(1,1);

	//把直方图归一化
	normalize(histRow,histRowDst,1,0,NORM_L1);
	FileStorage fs(argv[2],FileStorage::WRITE);
	//把histRowDst保存到.xml文件里
	fs << argv[3] << histRowDst;
	fs.release();
	return 0;
}


分别各自提取他们的一维颜色直方图



然后,在F盘出现了四个.xml文件,分别存放了他们的颜色直方图信息

____________________________________________________________________________________________________________________________________

第三步:利用颜色卡的颜色直方图检索图像的颜色直方图


原文地址:https://www.cnblogs.com/gcczhongduan/p/5374621.html