映像相似性(測試)–基於長條圖特徵的Image Search

來源:互聯網
上載者:User

轉自:http://blog.csdn.net/jia20003/article/details/7771651#comments

影像處理之相似圖片識別(長條圖應用篇)

演算法概述:

首先對源映像與要篩選的映像進行長條圖資料擷取,對採集的各自映像長條圖進行歸一化再

使用巴氏係數演算法對長條圖資料進行計算,最終得出映像相似性值,其值範圍在[0, 1]之間

0表示極其不同,1表示極其相似(相同)。

演算法步驟詳解:

大致可以分為兩步,根據源映像與候選映像的像素資料,產生各自長條圖資料。第二步:使

用第一步輸出的長條圖結果,運用巴氏係數(Bhattacharyya coefficient)演算法,計算出相似程

度值。

第一步:長條圖計算

長條圖分為灰階長條圖與RGB長條圖,對於灰階映像長條圖計算十分簡單,只要初始化一

個大小為256的長條圖數組H,然後根據像素值完成頻率分布統計,假設像素值為124,則

H[124] += 1, 而對於彩色RGB像素來說長條圖表達有兩種方式,一種是單一長條圖,另外一

種是三維長條圖,三維長條圖比較簡單明了,分別對應RGB三種顏色,定義三個長條圖HR,

HG, HB, 假設某一個像素點P的RGB值為(4, 231,129), 則對於的長條圖計算為HR[4] += 1,

HG[231] += 1, HB[129] += 1, 如此對每個像素點完成統計以後,RGB彩色長條圖資料就產生了。

而RGB像素的單一長條圖SH表示稍微複雜點,每個顏色的值範圍為0 ~ 255之間的,假設

可以分為一定範圍等份,當8等份時,每個等份的值範圍為32, 16等份時,每個等份值範

圍為16,當4等份時候,每個等份值的範圍為64,假設RGB值為(14, 68, 221), 16等份之

後,它對應長條圖索引值(index)分別為: (0, 4, 13), 根據計算索引值公式:index = R + G*16 + B*16*16

對應的長條圖index = 0 + 4*16 + 13 * 16 * 16, SH[3392] += 1

如此遍曆所有RGB像素值,完成長條圖資料計算。

第二步:巴氏係數計算,計算公式如下:


其中P, P’分別代表源與候選的映像長條圖資料,對每個相同i的資料點乘積開平方以後相加

得出的結果即為映像相似性值(巴氏係數因子值),範圍為0到1之間。

程式效果:

相似性超過99%以上,極其相似


相似性為:72%, 一般相似

程式長條圖計算原始碼如下:

[java]
view plaincopyprint?
  1. public void setGreenBinCount(int greenBinCount) { 
  2.     this.greenBins = greenBinCount; 
  3.  
  4. public void setBlueBinCount(int blueBinCount) { 
  5.     this.blueBins = blueBinCount; 
  6.  
  7. public float[] filter(BufferedImage src, BufferedImage dest) { 
  8.     int width = src.getWidth(); 
  9.        int height = src.getHeight(); 
  10.         
  11.        int[] inPixels =
    new int[width*height]; 
  12.        float[] histogramData =
    new float[redBins * greenBins * blueBins]; 
  13.        getRGB( src, 0,
    0, width, height, inPixels ); 
  14.        int index = 0; 
  15.        int redIdx =
    0, greenIdx = 0, blueIdx =0; 
  16.        int singleIndex = 0; 
  17.        float total =
    0; 
  18.        for(int row=0; row<height; row++) { 
  19.         int ta =
    0, tr = 0, tg =0, tb =
    0; 
  20.         for(int col=0; col<width; col++) { 
  21.             index = row * width + col; 
  22.             ta = (inPixels[index] >> 24) &0xff; 
  23.                tr = (inPixels[index] >>
    16) & 0xff; 
  24.                tg = (inPixels[index] >> 8) &0xff; 
  25.                tb = inPixels[index] &
    0xff; 
  26.                redIdx = (int)getBinIndex(redBins, tr,255); 
  27.                greenIdx = (int)getBinIndex(greenBins, tg,255); 
  28.                blueIdx = (int)getBinIndex(blueBins, tb,255); 
  29.                singleIndex = redIdx + greenIdx * redBins + blueIdx * redBins * greenBins; 
  30.                histogramData[singleIndex] += 1; 
  31.                total += 1; 
  32.         } 
  33.        } 
  34.         
  35.        // start to normalize the histogram data 
  36.        for (int i =0; i < histogramData.length; i++) 
  37.        { 
  38.         histogramData[i] = histogramData[i] / total; 
  39.        } 
  40.         
  41.        return histogramData; 
public void setGreenBinCount(int greenBinCount) {this.greenBins = greenBinCount;}public void setBlueBinCount(int blueBinCount) {this.blueBins = blueBinCount;}public float[] filter(BufferedImage src, BufferedImage dest) {int width = src.getWidth();        int height = src.getHeight();                int[] inPixels = new int[width*height];        float[] histogramData = new float[redBins * greenBins * blueBins];        getRGB( src, 0, 0, width, height, inPixels );        int index = 0;        int redIdx = 0, greenIdx = 0, blueIdx = 0;        int singleIndex = 0;        float total = 0;        for(int row=0; row<height; row++) {        int ta = 0, tr = 0, tg = 0, tb = 0;        for(int col=0; col<width; col++) {        index = row * width + col;        ta = (inPixels[index] >> 24) & 0xff;                tr = (inPixels[index] >> 16) & 0xff;                tg = (inPixels[index] >> 8) & 0xff;                tb = inPixels[index] & 0xff;                redIdx = (int)getBinIndex(redBins, tr, 255);                greenIdx = (int)getBinIndex(greenBins, tg, 255);                blueIdx = (int)getBinIndex(blueBins, tb, 255);                singleIndex = redIdx + greenIdx * redBins + blueIdx * redBins * greenBins;                histogramData[singleIndex] += 1;                total += 1;        }        }                // start to normalize the histogram data        for (int i = 0; i < histogramData.length; i++)        {        histogramData[i] = histogramData[i] / total;        }                return histogramData;}

計算巴氏係數的代碼如下:

[java]
view plaincopyprint?
  1. /**
  2. * Bhattacharyya Coefficient
  3. * http://www.cse.yorku.ca/~kosta/CompVis_Notes/bhattacharyya.pdf
  4. *
  5. * @return
  6. */ 
  7. public double modelMatch() { 
  8.     HistogramFilter hfilter = new HistogramFilter(); 
  9.     float[] sourceData = hfilter.filter(sourceImage,null); 
  10.     float[] candidateData = hfilter.filter(candidateImage,null); 
  11.     double[] mixedData =new
    double[sourceData.length]; 
  12.     for(int i=0; i<sourceData.length; i++ ) { 
  13.         mixedData[i] = Math.sqrt(sourceData[i] * candidateData[i]); 
  14.     } 
  15.      
  16.     // The values of Bhattacharyya Coefficient ranges from 0 to 1, 
  17.     double similarity =
    0; 
  18.     for(int i=0; i<mixedData.length; i++ ) { 
  19.         similarity += mixedData[i]; 
  20.     } 
  21.      
  22.     // The degree of similarity 
  23.     return similarity; 
/** * Bhattacharyya Coefficient * http://www.cse.yorku.ca/~kosta/CompVis_Notes/bhattacharyya.pdf *  * @return */public double modelMatch() {HistogramFilter hfilter = new HistogramFilter();float[] sourceData = hfilter.filter(sourceImage, null);float[] candidateData = hfilter.filter(candidateImage, null);double[] mixedData = new double[sourceData.length];for(int i=0; i<sourceData.length; i++ ) {mixedData[i] = Math.sqrt(sourceData[i] * candidateData[i]);}// The values of Bhattacharyya Coefficient ranges from 0 to 1,double similarity = 0;for(int i=0; i<mixedData.length; i++ ) {similarity += mixedData[i];}// The degree of similarityreturn similarity;}

轉載文章請務必註明出自本部落格

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.