最接近色.docx

上传人:b****6 文档编号:5292166 上传时间:2022-12-14 格式:DOCX 页数:28 大小:24.50KB
下载 相关 举报
最接近色.docx_第1页
第1页 / 共28页
最接近色.docx_第2页
第2页 / 共28页
最接近色.docx_第3页
第3页 / 共28页
最接近色.docx_第4页
第4页 / 共28页
最接近色.docx_第5页
第5页 / 共28页
点击查看更多>>
下载资源
资源描述

最接近色.docx

《最接近色.docx》由会员分享,可在线阅读,更多相关《最接近色.docx(28页珍藏版)》请在冰豆网上搜索。

最接近色.docx

最接近色

◇最接近色

 

*最接近色搜尋方法研究-球殼範圍逼近法*

*作者:

邱奕南(Chi'uI-Nan)*

*版權聲明:

以下文章內容本人僅同意供BBS站上流傳學習,但必須完整流傳*

*(含版權聲明及程式),其餘權利一概保留。

任何未經本人同意*

*,將本文販賣、刊登、節錄、或其他一切侵害本人著作權之行為*

*者,皆需負擔刑事責任及民事賠償責任。

*

**********************************************************************

對於彩色影像的處理上,不管是處理抖色、更換色盤資料、或是全彩影像

轉色盤影像時,最接近色搜尋的速度往往決定這些影像處理的速度。

因此本文

的目的,便是要探討如何快速搜尋到最接近色。

首先將問題定義如下:

對於一個在RGB色彩空間、具有N個顏色的集合S={Ci},i=0~N-1,現給

定任一顏色C,請找出集合S中的一個顏色C',使得C與C'在RGB色彩空間上

的距離最接近。

由於RGB色彩空間可視為一個立方體的三度空間,因此我們可將整個問題轉換成

三度空間幾何上的問題:

假設三度空間上有N個點Pi,i=0~N-1。

現給定任一點P,請在這N個點中找

出另一點P',使得P與P'的距離最小。

解決這個問題最簡單的方法,便是循序搜尋法(SequentialSearch),也就是

算出每一個點Pi和點P的距離,然後一個點一個點的比較,自然便可找出和點P

距離最接近的點P'。

但是可想而知的是,這種方法的效率必然很差,因此我們

必須想辦法略去一些不必比較的點。

而要略去不必比較的點,首先便必須從目

前已算出最接近點的資訊上著手,由該點已算得的資訊略去一些必定較遠的點。

至於目前已算出最接近點中,有那些與距離相關的資訊可用來判斷某些未比較

點較遠呢?

我們先看下面的定理:

對於空間上點P和點Q,若其與原點O的距離為Rp和Rq,且點P和點Q的距離為

D,則D>=│Rp-Rq│。

證明:

三點O、P、Q成一三角形。

現已知OP=Rp,OQ=Rq,假設OP與OQ夾角為θ,則:

PQ=Sqrt(Rp^2+Rq^2-2RpRq*cosθ)

因此當θ=0(也就是OP與OQ重疊)時,PQ值最小,故

PQ>=Sqrt(Rp^2+Rq^2-2RpRq*cos0)=│Rp-Rq│

現在我們先假設已存在的N個點Pi,若其與原點距離為Ri,而給定點P,其與原

點距離為R,與點Pi距離為Di。

則當目前最接近點P'與點P的距離為D'時,任何

一點Pj,只要符合Dj>=D'時,由於其距離不會比較近,因此便不需去比較這

個點Pj了。

然而我們並未算出Dj的值呀?

這時候便可用上面的定理了。

當下式

成立時:

D'<=abs(R-Rj)

由於abs(R-Rj)<=Dj,因此D'<=Dj。

也就是說,只要任何一點Pj,其與原點

距離Rj代入上式成立時,便不需去比較了。

從另外一個角度來看,若我們已算

出目前最接近點與點P的距離D'時,則所有與原點相距在(R-D',R+D')範圍以外

的其他點都不必再去比較了。

接下來我們再考慮距離的計算方式。

一般距離的定義為sqrt(x^2+y^2+z^2),

但由於必須有三個乘法且必須開根號,其速度會慢很多。

因此,我們可以將色

彩距離的定義改為:

D'=│R-Rj│+│G-Gj│+│B-Bj│

由於

│R-Rj│+│G-Gj│+│B-Bj│>=│(R-Rj)+(G-Gj)+(B-Bj)│

因此D'<=abs(R-Rj)的式子依然成立。

如此在距離的計算上速度會比較快些。

至於採用這種距離定義,效果是否會變得太差?

這點倒不用擔心。

因為不管是

在影像處理或地貌比對上,絕對誤差和常用來取代平方誤差和,其效果雖較差

些,但差異並不大。

這點作者也實際驗證過。

最後我們將整個搜尋最接近色的

演算法列出如下:

1.算出顏色集合S中,每個顏色Ci與原點的距離Ri,並依Ri值大小排序好。

這個部份可事先算好。

2.算出給定顏色C與原點的距離R。

3.取出顏色集合中與原點距離亦為R(或附近)的顏色C',並計算與顏色C

的距離為D',得到搜尋範圍(R-D',R+D')。

4.取出搜尋範圍(R-D',R+D')中尚未比較過的點C",並計算與顏色C的距離

為D"。

若D"

5.重複步驟4,直到搜尋範圍(R-D',R+D')中已無尚未比較過的點。

此時,

C'即為所要搜尋的最接近色。

現在我們已得到一種快速搜尋最接近色的方法了,但是我們要如何寫成程

式呢?

對於搜尋範圍的逼近,以及已比較點的略去,我們可以從已排序好的色

盤資料中,由初始計算(距離R)的顏色索引值開始往兩方向逐點計算,直到兩

方向所計算的顏色原點距均超出搜尋範圍為止。

至於顏色索引值的更新方式有

兩種,一種是依目前比較的顏色索引值漸增及漸減,一種是對目前搜尋距離值

漸增及漸減(利用距離區間的方式記錄應比較的顏色索引值)。

直覺上,前者

的速度應比後者快。

以下是這兩種方法的程式部份:

 

(一)顏色索引值增減逼近法

staticintColor_No;/*顏色數*/

staticunsignedcharUse_Palette[3][256];/*改變索引方式,以加速取值*/

staticunsignedcharPalette_Index[256];/*與原調色盤對應之索引值*/

staticunsignedintRGB_Distance[256];/*各顏色與原點距離*/

staticunsignedcharDistance_Index[765+1];/*相同原點距離索引值*/

voidSetPalette(intcolor_no,unsignedchar*palette)

{

/*------------------------------------------------------------

作用:

設定使用的調色盤資料

參數:

color_no=色彩數,1~256。

palette=色盤資料,依次為RGB,每色3byte。

------------------------------------------------------------*/

inti,j,min_index,min_distance,cur_distance,temp;

/*計算與原點距離*/

Color_No=color_no;

for(i=0;i

{

Palette_Index[i]=i;

RGB_Distance[i]=palette[i*3]+palette[i*3+1]+palette[i*3+2];

}

/*依原點距離排序-使用MinimaxSort*/

cur_distance=0;

Distance_Index[0]=0;

for(i=0;i

{

/*找出最小原點距離者*/

min_distance=RGB_Distance[i];

min_index=i;

for(j=i+1;j

if(RGB_Distance[j]

{

min_distance=RGB_Distance[j];

min_index=j;

}

/*將最小者調上來*/

j=Palette_Index[min_index];

Palette_Index[min_index]=Palette_Index[i];

Palette_Index[i]=j;

temp=RGB_Distance[min_index];

RGB_Distance[min_index]=RGB_Distance[i];

RGB_Distance[i]=temp;

/*記錄調色盤資料*/

Use_Palette[0][i]=palette[j*3];

Use_Palette[1][i]=palette[j*3+1];

Use_Palette[2][i]=palette[j*3+2];

/*更新距離索引範圍*/

for(j=cur_distance+1;j<=min_distance;j++)Distance_Index[j]=i;

cur_distance=min_distance;

}

for(j=cur_distance+1;j<=765;j++)Distance_Index[j]=color_no-1;

}

intGetNearestColor(intr,intg,intb)

{

/*------------------------------------------------------------

作用:

取得最接近色之索引值

參數:

r,g,b=RGB三色分量值

傳回:

最接近色在色盤資料上的索引值

限制:

呼叫前必須呼叫SetPalette設定使用之調色盤資料

------------------------------------------------------------*/

intmin_index,min_distance,distance,left_bound,right_bound;

intcur_distance,left_index,right_index;

intleft_distance,right_distance,left_ok,right_ok;

/*初始化:

先比較相同距離之色彩

色彩索引值可由Distance_Index中直接取得*/

distance=r+g+b;

left_index=right_index=min_index=Distance_Index[distance];

min_distance=abs(r-Use_Palette[0][min_index])+

abs(g-Use_Palette[1][min_index])+

abs(b-Use_Palette[2][min_index]);

/*搜尋至超出範圍為止

搜尋範圍:

distance-min_distance~distance+min_distance

left_index,right_index:

兩方向目前比較的顏色索引值

left_distance,right_distance:

兩方向目前已搜尋到的原點距

left_bound,right_bound:

兩方向的搜尋範圍

left_ok,right_ok:

兩方向是否已超出搜尋範圍旗標*/

left_ok=right_ok=false;

left_distance=right_distance=distance;

left_bound=distance-min_distance;

right_bound=distance+min_distance;

for(;;)

{

/*往右搜尋*/

if(!

right_ok)

if((++right_index>Color_No)||

((right_distance=RGB_Distance[right_index])>right_bound))

right_ok=true;

else

{

cur_distance=abs(r-Use_Palette[0][right_index])+

abs(g-Use_Palette[1][right_index])+

abs(b-Use_Palette[2][right_index]);

if(cur_distance

{

min_distance=cur_distance;

min_index=right_index;

left_bound=distance-min_distance;

right_bound=distance+min_distance;

if(left_distance

}

}

/*往左搜尋*/

if(!

left_ok)

if((--left_index<0)||

((left_distance=RGB_Distance[left_index])

left_ok=true;

else

{

cur_distance=abs(r-Use_Palette[0][left_index])+

abs(g-Use_Palette[1][left_index])+

abs(b-Use_Palette[2][left_index]);

if(cur_distance

{

min_distance=cur_distance;

min_index=left_index;

left_bound=distance-min_distance;

right_bound=distance+min_distance;

if(right_distance>right_bound)right_ok=true;

}

}

/*兩邊都超出範圍時,即結束搜尋*/

if(left_ok&&right_ok)break;

}

returnPalette_Index[min_index];

}

 

(二)搜尋距離值增減逼近法

staticunsignedcharUse_Palette[3][256];/*改變索引方式,以加速取值*/

staticunsignedcharPalette_Index[256];/*與原調色盤對應之索引值*/

staticunsignedcharDistance_Index[765/9+2];/*相同原點距離索引值*/

staticunsignedintDistance_Divide;/*區間分割距離*/

staticunsignedintMax_Divide;/*最大的區間索引值*/

voidSetPalette(intcolor_no,unsignedchar*palette)

{

/*------------------------------------------------------------

作用:

設定使用的調色盤資料

參數:

color_no=色彩數,1~256。

palette=色盤資料,依次為RGB,每色3byte。

------------------------------------------------------------*/

inti,j,min_index,min_distance,cur_distance;

unsignedchardistance[256];

/*決定分割區間數,目前儘量使得每個區間約有3個顏色

除數:

16色=144,256色=9*/

Distance_Divide=2304/color_no;

Max_Divide=765/Distance_Divide;

/*計算與原點距離*/

for(i=0;i

{

Palette_Index[i]=i;

distance[i]=(palette[i*3]+palette[i*3+1]+palette[i*3+2])/

Distance_Divide;

}

/*依原點距離排序-使用MinimaxSort*/

cur_distance=0;

Distance_Index[0]=0;

for(i=0;i

{

/*找出最小原點距離者*/

min_distance=distance[i];

min_index=i;

for(j=i+1;j

if(distance[j]

{

min_distance=distance[j];

min_index=j;

}

/*將最小者調上來*/

j=Palette_Index[min_index];

Palette_Index[min_index]=Palette_Index[i];

Palette_Index[i]=j;

distance[min_index]=distance[i];

/*記錄調色盤資料*/

Use_Palette[0][i]=palette[j*3];

Use_Palette[1][i]=palette[j*3+1];

Use_Palette[2][i]=palette[j*3+2];

/*更新距離索引範圍*/

for(j=cur_distance+1;j<=min_distance;j++)Distance_Index[j]=i;

cur_distance=min_distance;

}

for(j=cur_distance+1;j<=Max_Divide+1;j++)Distance_Index[j]=color_no;

}

intGetNearestColor(intr,intg,intb)

{

/*------------------------------------------------------------

作用:

取得最接近色之索引值

參數:

r,g,b=RGB三色分量值

傳回:

最接近色在色盤資料上的索引值

限制:

呼叫前必須呼叫SetPalette設定使用之調色盤資料

------------------------------------------------------------*/

inti,min_index,min_distance,cur_range,distance,end_index;

intcur_distance,search_range;

/*初始化:

搜尋相同距離區間之色彩*/

distance=(r+g+b)/Distance_Divide;

end_index=Distance_Index[distance+1];

min_distance=768;

for(i=Distance_Index[distance];i

{

cur_distance=abs(r-Use_Palette[0][i])+abs(g-Use_Palette[1][i])+

abs(b-Use_Palette[2][i]);

if(cur_distance

{

min_distance=cur_distance;

min_index=i;

}

}

/*搜尋至超出範圍為止

搜尋範圍:

distance-search_range~distance+search_range*/

cur_range=1;

search_range=min_distance/Distance_Divide+1;

while(cur_range<=search_range)

{

/*往左搜尋一個區間*/

if(distance-cur_range>=0)

{

end_index=Distance_Index[distance-cur_range+1];

for(i=Distance_Index[distance-cur_range];i

{

cur_distance=abs(r-Use_Palette[0][i])+

abs(g-Use_Palette[1][i])+

abs(b-Use_Palette[2][i]);

if(cur_distance

{

min_distance=cur_distance;

min_index=i;

search_range=min_distance/Distance_Divide+1;

}

}

}

/*往右搜尋一個區間*/

if(distance+cur_range<=Max_Divide)

{

end_index=Distance_Index[distance+cur_range+1];

for(i=Distance_Index[distance+cur_range];i

{

cur_distance=abs(r-Use_Palette[0][i])+

abs(g-Use_Palette[1][i])+

abs(b-Use_Palette[2][i]);

if(cur_distance

{

min_distance=cur_distance;

min_index=i;

search_range=min_distance/Distance_Divide+1;

}

}

}

cur_range++;

}

returnPalette_Index[min_index];

}

 

上面兩個程式,我們以標準調色盤資料為準,R、G、B各以4倍增,全部呼叫次

數為262144次來做分析。

首先測得兩種方法的平均比較次數:

│循序搜尋法│程式一│倍差│程式二│倍差

───┼─────┼─────┼───┼─────┼───

16色│16次│5.5次│2.9│10.0次│1.6

256色│256次│39.9次│6.4│48.1次│5.3

因此在理論上來講,程式一的速度應較快。

但是實際在486DX2-66測試而得的速

度如下:

│循序搜尋法│程式一│倍差│程式二│倍差

───┼──

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 高等教育 > 院校资料

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1