光照問題之常見算法比較(附Python代碼)

 1、灰度世界算法html

① 算法原理python

灰度世界算法以灰度世界假設爲基礎,該假設認爲:對於一幅有着大量色彩變化的圖像,R,G,B三個份量的平均值趨於同一灰度值Gray。從物理意義上講,灰色世界法假設天然界景物對於光線的平均反射的均值在整體上是個定值,這個定值近似地爲「灰色」。顏色平衡算法將這一假設強制應用於待處理圖像,能夠從圖像中消除環境光的影響,得到原始場景圖像。算法

通常有兩種方法肯定Gray值網絡

1) 使用固定值,對於8位的圖像(0~255)一般取128做爲灰度值app

2) 計算增益係數,分別計算三通道的平均值avgR,avgG,avgB,則:dom

Avg=(avgR+avgG+avgB)/3函數

kr=Avg/avgR , kg=Avg/avgG , kb=Avg/avgB學習

利用計算出的增益係數,從新計算每一個像素值,構成新的圖片ui

② 算法優缺點spa

這種算法簡單快速,可是當圖像場景顏色並不豐富時,尤爲出現大塊單色物體時,該算法常會失效。

③ 算法展現

 1 def grey_world(nimg):  
 2    nimg = nimg.transpose(2, 0, 1).astype(np.uint32)  
 3    avgB = np.average(nimg[0])  
 4    avgG = np.average(nimg[1])  
 5    avgR = np.average(nimg[2])  
 6  
 7    avg = (avgB + avgG + avgR) / 3  
 8  
 9    nimg[0] = np.minimum(nimg[0] * (avg / avgB), 255)  
10    nimg[1] = np.minimum(nimg[1] * (avg / avgG), 255)  
11    nimg[2] = np.minimum(nimg[2] * (avg / avgR), 255)  
12    return  nimg.transpose(1, 2, 0).astype(np.uint8)  

 

① 效果圖對比

       

 

     

 第一組圖片場景顏色豐富,利用灰度世界假設法校訂效果明顯;第二組圖片中顏色相對單一,校訂效果也不是很理想;這也就致使了‘灰度世界假設算法’沒法通用.

 

2、直方圖均衡化

① 算法原理

直方圖均衡化的基本思想是把原始圖的直方圖變換爲均勻分佈的形式,這樣就增長了象素灰度值的動態範圍從而可達到加強圖像總體對比度的效果

    假設,一張圖像的直方圖以下圖(左)所示,均衡化後,圖像直方圖以下圖(右)顯示

     

 

② 算法優缺點

 直方圖均衡化,通常可用於灰度圖像的對比加強(如:人臉陰影部位加強);

若是直接對彩色圖像R,G,B三通道分別均衡化後再合併,極容易出現顏色不均、失真等問題,因此,通常會將RGB圖像轉換到YCrCb空間,對Y通道進行均衡化(Y通道表明亮度成分)

 

 ③ 算法展現

python中opencv3提供了能將灰度圖直接均衡化的方法:equalizeHist(img),藉助這個方法,能夠實現彩色圖像的均衡化

1 def hisEqulColor(img):  
2     ycrcb = cv2.cvtColor(img, cv2.COLOR_BGR2YCR_CB)  
3     channels = cv2.split(ycrcb)  
4     cv2.equalizeHist(channels[0], channels[0]) #equalizeHist(in,out)  
5     cv2.merge(channels, ycrcb)  
6     img_eq=cv2.cvtColor(ycrcb, cv2.COLOR_YCR_CB2BGR)  
7     return img_eq  

 

④ 效果圖對比

    

    

                                                       

第一組、第二組彩色圖像中均衡化後圖片對比原圖更清晰,細節突出;第三組灰度圖,均衡化在光照不均調節明暗的功能上,效果更明顯

 

 

3、視網膜-大腦皮層(Retinex)加強算法

① 算法原理

    視網膜-大腦皮層(Retinex)理論認爲世界是無色的,人眼看到的世界是光與物質相互做用的結果,也就是說,映射到人眼中的圖像和光的長波(R)、中波(G)、短波(B)以及物體的反射性質有關

                                                                                                                                                        

                                                                                                                                                                    

其中I是人眼中看到的圖像,R是物體的反射份量,L是環境光照射份量,(x, y)是二維圖像對應的位置

它經過估算L來計算R,具體來講,L能夠經過高斯模糊和I作卷積運算求得,用公式表示爲

其中F是高斯模糊的濾波器,「 * 」表示卷積運算

 

其中σ稱爲高斯周圍空間常數(Gaussian Surround Space Constant),也就是算法中所謂的尺度,對圖像處理有比較大的影響,對於二維圖像,等於對應位置即:

即:通常認爲光照份量是原圖像通過高斯濾波後的結果

 

② 算法優缺點

Retinex算法,從SSR(單尺度Retinex)到MSR(多尺度Retinex)以及到最經常使用的MSRCR(帶顏色恢復的多尺度Retinex);其中色彩恢復主要目的是來調節因爲圖像局部區域對比度加強而致使顏色失真的缺陷.

先看一組公式:

RMSRCR(x,y)'=G⋅RMSRCR(x,y)+b

RMSRCR (x,y)=C(x,y)RMSR(x,y)

C(x,y)=f[I'(x,y)]=f[I(x,y)/∑I(x,y)]Ci(x,y)=f[Ii′(x,y)]=f[Ii(x,y)∑j=1NIj(x,y)] 

f[I'(x,y)]=βlog[αI'(x,y)]=β{log[αI'(x,y)]−log[∑I(x,y)]}

若是是灰度圖像,只須要計算一次便可,若是是彩色圖像,如RGB三通道,則每一個通道均須要如上進行計算

G表示增益Gain(通常取值:5)

b表示誤差Offset(通常取值:25)

I (x, y)表示某個通道的圖像

C表示某個通道的彩色回覆因子,用來調節3個通道顏色的比例;

f(·)表示顏色空間的映射函數;

β是增益常數(通常取值:46)

α是受控制的非線性強度(通常取值:125)

MSRCR算法利用彩色恢復因子C,調節原始圖像中3個顏色通道之間的比例關係,從而把相對較暗區域的信息凸顯出來,達到了消除圖像色彩失真的缺陷。 處理後的圖像局部對比度提升,亮度與真實場景類似,在人們視覺感知下,圖像顯得更加逼真可是MSRCR算法處理圖像後,像素值通常會出現負值。因此從對數域r(x, y)轉換爲實數域R(x, y)後,須要經過改變增益Gain,誤差Offset對圖像進行修正

 關於Retinex算法更多的細節,能夠查看https://www.cnblogs.com/wangyong/p/8665434.html

 

③ 算法展現

 

④  效果圖對比

      

                             (原圖)                                                                                           (SSR)

 

     

                                       (MSR)                                                                            (MSRCR)

  

       

                                  (原圖)                                                                                     (SSR) 

 

      

                                  (MSR)                                                                                    (MSRCR)

上面的兩組圖片,能夠看到第一組的效果明顯,第二組的效果不好;同時可和‘灰度世界算法’的結果進行比較;通常認爲,Retinex算法比較適合航空圖片的處理,‘去霧’效果顯著。

 

4、自動白平衡(AWB)

① 算法原理

 用一個簡單的概念來解釋什麼是白平衡:假設,圖像中R、G、B最高灰度值對應於圖像中的白點,最低灰度值的對應於圖像中最暗的點;其他像素點利用(ax+b)映射函數把彩色圖像中R、G、B三個通道內的像素灰度值映射到[0.255]的範圍內.

白平衡的本質是讓白色的物體在任何顏色的光源下都顯示爲白色,這一點對人眼來講很容易辦到,由於人眼有自適應的能力,只要光源的色彩不超出必定的限度,就能夠自動還原白色。但相機就不一樣了,不管是圖像傳感器仍是膠捲都會記錄光源的顏色,白色的物體就會帶上光源的顏色,白平衡所要作的就是把這個偏色去掉。

 

 ② 算法優缺點

自動白平衡是一個很複雜的問題,目前尚未一個萬能的方法能夠解決全部場景的白平衡問題

截止2017年,出現很多利用神經網絡實現自動白平衡的算法,也會有專門的文檔對這部分進行詳細的介紹。

 

③ 算法展現

利用Lab顏色空間,對圖片進行自動白平衡操做.

 

③ 效果圖對比

       

 

    

能夠看出,這兩組效果圖和‘灰度世界假設’算法得出的效果圖很相似,主要是由於上述的白平衡算法也是基於‘灰度世界’這個假設下的

 

 

5、自動色彩均衡(ACE)

① 算法原理

ACE算法源自retinex算法,能夠調整圖像的對比度,實現人眼色彩恆常性和亮度恆常性,該算法考慮了圖像中顏色和亮度的空間位置關係,進行局部特性的自適應濾波,實現具備局部和非線性特徵的圖像亮度與色彩調整和對比度調整,同時知足灰色世界理論假設和白色斑點假設。

第一步:對圖像進行色彩/空域調整,完成圖像的色差校訂,獲得空域重構圖像;

式中,Rc 是中間結果,Ic(p)-Ic(j)爲兩個不一樣點的亮度差,d(p,j)表示距離度量函數,r(*)爲亮度表現函數,需是奇函數;這一步能夠適應局部圖像對比度,r(*)可以放大較小的差別,並豐富大的差別,根據局部內容擴展或者壓縮動態範圍。通常得,r(*)爲:

第二步:對校訂後的圖像進行動態擴展。ACE算法是對單一色道進行的,對於彩色圖片須要對每個色道分別處理

    其中存在一種簡單的線性擴展:

    R(x)=round[127.5+w*Rc(p)],其中,w表示線段[(0,mc),(255,Mc)]的斜率,且有:

    Mc=min[Rc(p)],Mc=max[Rc(p)]

 

 第三步:利用下面的公式將R(x)展到[0,1]之間,獲得加強後的通道

 

 

②算法優缺點

ACE的加強效果廣泛retinex好。須要注意的是,ACE中當前像素是與整個圖像的其餘像素作差分比較,計算複雜度很是很是高,這也是限制它應用的最主要緣由

因此,通常算法中,會經過指定採樣數來代替與整副圖像的像素點信息進行差分計算,減小運算量,提升效率。

 

③ 算法展現

  1 #飽和函數  
  2 def calc_saturation(diff,slope,limit):  
  3     ret = diff * slope  
  4     if ret > limit:  
  5         ret = limit  
  6     elif (ret < (-limit)):  
  7         ret = -limit  
  8     return ret  
  9  
 10 def automatic_color_equalization(nimg, slope=10, limit=1000, samples=500):  
 11  
 12     nimg = nimg.transpose(2, 0, 1)  
 13   
 14     #Convert input to an ndarray with column-major memory order(僅僅是地址連續,內容和結構不變)  
 15     nimg = np.ascontiguousarray(nimg, dtype=np.uint8)  
 16 
 17     width=nimg.shape[2]  
 18     height=nimg.shape[1]  
 19   
 20     cary=[]  
 21   
 22     #隨機產生索引  
 23     for i in range(0,samples):  
 24         _x=random.randint(0,width)%width  
 25         _y=random.randint(0,height)%height  
 26  
 27         dict={"x":_x,"y":_y}  
 28         cary.append(dict)  
 29  
 30  
 31    mat=np.zeros((3,height,width),float)  
 32   
 33    r_max = sys.float_info.min  
 34    r_min = sys.float_info.max  
 35  
 36    g_max = sys.float_info.min  
 37    g_min = sys.float_info.max  
 38   
 39    b_max = sys.float_info.min  
 40    b_min = sys.float_info.max  
 41   
 42   for i in range(height):  
 43         for j in range(width):  
 44             r=nimg[0,i,j]  
 45             g=nimg[1,i,j]  
 46             b=nimg[2,i,j]  
 47 
 48             r_rscore_sum = 0.0  
 49             g_rscore_sum = 0.0  
 50             b_rscore_sum = 0.0  
 51             denominator = 0.0  
 52   
 53            for _dict in cary:  
 54                 _x=_dict["x"#width  
 55                 _y=_dict["y"#height  
 56   
 57                 #計算歐氏距離  
 58                 dist=np.sqrt(np.square(_x-j)+np.square(_y-i))  
 59                 if (dist < height / 5):  
 60                     continue;  
 61  
 62                 _sr=nimg[0,_y,_x]  
 63                 _sg=nimg[1,_y,_x]  
 64                 _sb=nimg[2,_y,_x]  
 65   
 66                 r_rscore_sum +=calc_saturation(int(r) - int(_sr),slope,limit) / dist  
 67                 g_rscore_sum +=calc_saturation(int(g) - int(_sg),slope,limit) / dist  
 68                 b_rscore_sum +=calc_saturation(int(b) - int(_sb),slope,limit) / dist  
 69  
 70                 denominator += limit / dist  
 71  
 72             r_rscore_sum = r_rscore_sum / denominator  
 73             g_rscore_sum = g_rscore_sum / denominator  
 74             b_rscore_sum = b_rscore_sum / denominator  
 75   
 76             mat[0,i,j]=r_rscore_sum  
 77             mat[1,i,j]=g_rscore_sum  
 78             mat[2,i,j]=b_rscore_sum  
 79  
 80             if r_max<r_rscore_sum:  
 81                 r_max=r_rscore_sum  
 82             if r_min>r_rscore_sum:  
 83                 r_min=r_rscore_sum  
 84   
 85             if g_max<g_rscore_sum:  
 86                 g_max=g_rscore_sum  
 87             if g_min>g_rscore_sum:  
 88                 g_min=g_rscore_sum  
 89   
 90             if b_max<b_rscore_sum:  
 91                 b_max=b_rscore_sum  
 92             if b_min>b_rscore_sum:  
 93                 b_min=b_rscore_sum  
 94   
 95    for i in range(height):  
 96         for j in range(width):  
 97            nimg[0, i, j] = (mat[0, i, j] - r_min) * 255 / (r_max - r_min)  
 98            nimg[1, i, j] = (mat[1, i, j] - g_min) * 255 / (g_max - g_min)  
 99            nimg[2, i, j] = (mat[2, i, j] - b_min) * 255 / (b_max - b_min)  
100   
101    return nimg.transpose(1, 2, 0).astype(np.uint8)

 

④ 效果圖對比

        

 

      

 

總結:查看各類傳統算法的效果圖,ACE自動色彩均衡算法具備比較好的廣泛性和效果,固然,對於一些圖片ACE也不能獲得很好地效果,因此,這就須要咱們不斷的去深刻研究和學習,接下來會學習神經網絡在色彩恆常性方面的應用並進行效果對比。

 

做爲一枚技術小白,寫這篇筆記的時候參考了不少博客論文,在這裏表示感謝,同時,轉載請註明出處......

相關文章
相關標籤/搜索