【1】稀疏表示與匹配追蹤

轉自:http://blog.csdn.net/jbb0523/article/details/45099655

題目:稀疏表示與匹配追蹤

        如果研究壓縮感知重構算法,那麼匹配追蹤絕對是一個繞不過去的概念,雖然最原始的匹配追蹤算法應用於重構的文獻並不多,但基於匹配追蹤改進後的正交匹配追蹤算法在研究壓縮感知的人羣中可以說是家喻戶曉、人盡皆知的。既然匹配追蹤是與重構有關的,爲什麼本篇取名爲《稀疏表示與匹配追蹤》呢?一個重構算法與稀疏表示有什麼關係?一般文獻中講到匹配追蹤所引參考文獻均爲文獻[1],而文獻[1]就是在講解基於匹配追蹤算法的信號稀疏表示問題,這到底是怎麼回事呢?(我想一個沒有做過稀疏表示的人直接來學習研究壓縮感知應該會有此問吧,比如說本人)。以下思路參考或直接引用了文獻[2]中的內容。

        在前面的“壓縮感知稀疏基之XXX”系列博文裏,實際是介紹了多種正交變換,給出了每一種正交變換的正交變換矩陣(正交基)。然而用正交基稀疏表達一個信號也有很多缺點,因爲一組基表達信號的能力取決於信號的特徵是否與基向量的特徵相吻合;例如,光滑連續信號可以被傅里葉基稀疏的表達,但脈衝信號就不行;再如,帶有孤立不連續點的平滑信號可以被小波基稀疏表達,但小波基在表達傅里葉頻譜中有窄帶高頻支撐的信號時卻是無效的。現實世界中的信號經常包含有用單一基所不能表達的特徵。對於這些信號,你或許希望可以選擇來自不同基的向量(如用小波基和傅里葉基來聯合表達一個信號)。因爲你想保證你可以表達一個信號空間的所有信號向量,所以由所有可選向量組成的字典應該能夠張成這個信號空間。然而由於這組字典中的向量來自不同的基,它們可能不是線性獨立的。由於這組字典中的向量不是線性獨立的,會造成用這組字典做信號表達時係數不唯一。然而如果創建一組冗餘字典,你就可以把你的信號展開在一組可以適應各種時頻或時間-尺度特性的向量上。這樣構造的字典可以極大地增加你稀疏表達各種特性信號的能力。

        例如三維空間中有基向量vx=(1,0,0),vy=(0,1,0),vz=(0,0,1),三維空間中的任意向量均可由三個基向量唯一表示,如v1=(1,2,3)= vx+2 vy +3 vz。然而若取三維空間的一組冗餘字典va=(1,1,1),vb=(1,1,2),vc=(2,1,1),vd=(1,2,4),這時若用這四個向量表示v1則有無窮多種表示方法,如v1=2va+ vbvcv1=vavb + vd。當然,這個用矩陣的方法理解更容易,第一種情況求係數是三個獨立的方程三個未知數,解唯一;第二種情況是三個方程四個未知數,必然有無窮多解。問題來了,既然在冗餘字典裏信號表達時的係數不唯一,那麼是否存在一種最好的表達方式呢?

        定義表達你的信號空間的歸一化基本模塊作爲字典。這些歸一化向量叫做原子。如果字典的原子張成了整個信號空間,那麼字典就是完全的。如果有原子之間線性相關,那麼字典就是冗餘的。在大多數匹配追蹤的應用中,字典都是完全且冗餘的。

        假設{φk}表示字典的原子。假設字典是完全且冗餘的。使用字典的線性組合表達信號將是不唯一的。


        一個重要的問題是是否存在一種最好的表達方式,一種直觀的最好方式是選擇φk使得近似信號和原始信號有最大的內積,如最好的φk滿足


即對於正交原子,爲投影到由φk張成的子空間上的幅值。匹配追蹤的中心問題是你如何選擇信號在字典中最優的M個展開項。

        用Φ={φk}表示一個原子歸一化的字典,x表示信號。匹配追蹤算法流程如下:

        (1)首先初始化殘差e0=x

        (2)匹配追蹤的第一步是從字典中找到與e0的內積絕對值最大的原子,表示爲φ1

        (3)通過從e0減去其在φ1所張成空間上的正交投影得到殘差e1


其中<e0, φ1>表示e0φ1的內積。由於已經說明Φ爲原子歸一化的字典,即φ1爲單位列向量,所以e0φ1所張成空間上的正交投影可以表示爲<e0, φ1>φ1 (由於爲一個向量,所以e0φ1所張成空間上的正交投影即爲e0φ1方向上的正交投影分量),若φ1不是單位列向量,則e0φ1方向上的正交投影分量爲<e0, φ1>φ1/(φ1Tφ1),其中上標T表示轉置。

        (4)對殘差迭代執行(2)、(3)步;


其中φm+1是從字典中找到與em的內積絕對值最大的原子。

        (5)直到達到某個指定的停止準則後停止算法。

        第(4)步對應到文獻[1]中爲文獻中的式(12):


        這裏要從數學上說明一點:由於內積<em, φm+1>實際上爲一個數(標量),所以


若令P=φm+1 (φTm+1φm+1)-1φTm+1 ,則第(4)步的迭代公式爲


注意矩陣P每次迭代都是不同的。

        在匹配追蹤(MP)中,字典原子不是相互正交的向量。因此上面減去投影計算殘差的過程中會再次引入與前面使用的原子不正交的成分。

        爲了更形象的看出這點,下面的例子非常清晰地展現了每一個細節(這是一個類比,不代表匹配追蹤過程)。考慮歐幾里得二維空間的歸一化框架字典


假設有如下信號


這個例子如圖所示,字典原子以紅色表示,信號向量藍色表示


        在matlab中如下創建此字典和信號:

[plain] view plain copy
  1. dictionary = [1 0; 1/2 sqrt(3)/2;-1/sqrt(2) -1/sqrt(2)]';  
  2. x = [1 1/2]';  

        計算信號和字典原子的內積:

[plain] view plain copy
  1. scalarproducts = dictionary'*x  

        輸出爲:

[plain] view plain copy
  1. scalarproducts =  
  2.     1.0000  
  3.     0.9330  
  4.    -1.0607  

        內積絕對值最大的是第3個原子[-1/sqrt(2); -1/sqrt(2)]。這也很容易理解,因爲兩者之間的夾角約爲π。從信號中減去信號在此原子上的正交投影得到殘差:

[plain] view plain copy
  1. residual = x-scalarproducts(3)*dictionary(:,3)  
        輸出爲:
[plain] view plain copy
  1. residual =  
  2.     0.2500  
  3.    -0.2500  

        可以驗證此時residual與原子[-1/sqrt(2); -1/sqrt(2)]正交。再次計算信號和字典原子的內積:

[plain] view plain copy
  1. scalarproducts = dictionary'*x  

       輸出爲:

 scalarproducts =

[plain] view plain copy
  1.  0.2500  
  2. -0.0915  
  3. -0.0000  
        第三個值爲0,這也說明residual與第3個原子[-1/sqrt(2);-1/sqrt(2)]正交。現在內積絕對值最大的是第1個原子[1;0](內積值爲0.25)。從信號中減去信號在此原子上的正交投影得到殘差:

[plain] view plain copy
  1. residual = residual-scalarproducts(1)*dictionary(:,1)  

        輸出爲:

[plain] view plain copy
  1. residual =  
  2.          0  
  3.    -0.2500  

        可以驗證此時residual與第1個原子[1;0]正交。再次計算信號和字典原子的內積:

[plain] view plain copy
  1. scalarproducts = dictionary'*x  

        輸出爲:

[plain] view plain copy
  1. scalarproducts =  
  2.          0  
  3.    -0.2165  
  4.     0.1768  

        第一個值爲0,這也說明residual與第1個原子[1;0]正交;但同時也應當注意到第3個值不再爲零,也就是說此時residual與第3個原子[-1/sqrt(2);-1/sqrt(2)]不再正交,這意味着這個原子有可能被再次選擇到。這個事實及與收斂相關的問題在正交匹配追蹤中得以解決。現在內積絕對值最大的是第2個原子[1/2;sqrt(3)/2](內積值爲-0.2165)。從信號中減去信號在此原子上的正交投影得到殘差:

[plain] view plain copy
  1. residual = residual-scalarproducts(2)*dictionary(:,2)  

        輸出爲:

[plain] view plain copy
  1. residual =  
  2.     0.1083  
  3.    -0.0625  

        到這裏可能你會發現一個問題:三個原子都選擇了一遍,但現在的residual仍然不爲零;而二維空間中任意兩個線性無關的二維向量即可生成整個二維空間,在這個例子中,三個列向量(原子)兩兩都是線性無關的,即我們要稀疏表達的信號x實際上可以由三個原子中任意兩個的線性組合表示。將三個原子中的任意兩個再加上信號x組合一個矩陣,用Matlab函數rref將矩陣化簡爲行階梯最簡形(Reduced row echelon form):

[plain] view plain copy
  1. rref([dictionary(:,1) dictionary(:,2) x])  
  2. rref([dictionary(:,1) dictionary(:,3) x])  
  3. rref([dictionary(:,2) dictionary(:,3) x])  

        三行代碼的輸出分別爲:

[plain] view plain copy
  1. ans =  
  2.     1.0000         0    0.7113  
  3.          0    1.0000    0.5774  
  4. ans =  
  5.     1.0000         0    0.5000  
  6.          0    1.0000   -0.7071  
  7. ans =  
  8.     1.0000         0   -1.3660  
  9.          0    1.0000   -2.3801  

        由以上輸出可以知道用其中任意兩個原子表示x時的組合係數。下面把上面所有程序給出:

[plain] view plain copy
  1. dictionary = [1 0; 1/2 sqrt(3)/2;-1/sqrt(2) -1/sqrt(2)]';  
  2. x = [1 1/2]';  
  3. scalarproducts = dictionary'*x  
  4. residual = x-scalarproducts(3)*dictionary(:,3)  
  5. scalarproducts = dictionary'*residual  
  6. residual = residual-scalarproducts(1)*dictionary(:,1)  
  7. scalarproducts = dictionary'*residual  
  8. residual = residual-scalarproducts(2)*dictionary(:,2)  
  9. rref([dictionary(:,1) dictionary(:,2) x])  
  10. rref([dictionary(:,1) dictionary(:,3) x])  
  11. rref([dictionary(:,2) dictionary(:,3) x])  

        雖然所有3個原子均選擇了一遍後殘差仍不爲零,但如果繼續迭代,殘差將會越來越小,程序如下(以下迭代5*N=5*3=15次):

[plain] view plain copy
  1. dictionary = [1 0; 1/2 sqrt(3)/2;-1/sqrt(2) -1/sqrt(2)]';  
  2. x = [1 1/2]';  
  3. [M,N] = size(dictionary);  
  4. residual = zeros(M,5*N+1);%殘差矩陣,保存每次迭代後的殘差  
  5. residual(:,1) = x;%初始化殘差爲x  
  6. L = size(residual,2);%得到殘差矩陣的列  
  7. pos_mm = zeros(1,L);%用來保存每次選擇的列序號  
  8. resi_norm = zeros(1,L);%用來保存每次迭代後的殘差的2範數  
  9. resi_norm(1) = norm(x);%因爲前面已初始化殘差爲x  
  10. for mm = 1:length(residual)  
  11.     %求出dictionary每列與上次殘差的內積  
  12.     scalarproducts = dictionary'*residual(:,mm);  
  13.     %找到內積中最大的列及其內積值  
  14.     [val,pos] = max(abs(scalarproducts));  
  15.     %更新殘差  
  16.     residual(:,mm+1) = residual(:,mm) - ...  
  17.         scalarproducts(pos)*dictionary(:,pos);  
  18.     %計算殘差的2範數(平方和再開根號)  
  19.     resi_norm(mm+1) = norm(residual(:,mm+1));  
  20.     %保存選擇的列序號  
  21.     pos_mm(mm+1) = pos;  
  22. end  
  23. %繪出殘差的2範數曲線  
  24. plot(resi_norm);grid;  


        將pos_mm輸出:pos_mm=[0 3 1 2 1 2 1 2 1 2 1 2 1 2 1 2 1],從第4次往後,交替選擇第1個原子和第2個原子。有關採用匹配追蹤算法在冗餘字典中稀疏表達實際的信號可參見參考文獻[3]。

        在正交匹配追蹤OMP中,殘差是總與已經選擇過的原子正交的。這意味着一個原子不會被選擇兩次,結果會在有限的幾步收斂。OMP的算法如下

        (1)用x表示你的信號,初始化殘差e0=x

        (2)選擇與e0內積絕對值最大的原子,表示爲φ1

        (3)將選擇的原子作爲列組成矩陣Φt,定義Φt列空間的正交投影算子爲


通過從e0減去其在Φt所張成空間上的正交投影得到殘差e1


        (4)對殘差迭代執行(2)、(3)步;


其中I爲單位陣。需要注意的是在迭代過程中Φt爲所有被選擇過的原子組成的矩陣,因此每次都是不同的,所以由它生成的正交投影算子矩陣P每次都是不同的。有關正交投影的概念可以參見《壓縮感知中的數學知識:投影矩陣(projectionmatrix)》。

        (5)直到達到某個指定的停止準則後停止算法。

        可以看出OMP與MP的不同根本在於殘差更新過程:OMP減去的Pemem所有被選擇過的原子組成的矩陣Φt所張成空間上的正交投影,而MP減去的Pemem本次被選擇的原子φm所張成空間上的正交投影。基於此,OMP可以保證已經選擇過的原子不會再被選擇。

        有關正交匹配追蹤的進一步分析見下一篇《施密特(Schimidt)正交化與正交匹配追蹤》,有關究竟爲什麼把稀疏表示與匹配追蹤放在一起參見下下篇《正交匹配追蹤(OMP)在稀疏分解與壓縮感知重構中的異同》。

        推薦一篇有關匹配追蹤與正交匹配追蹤的詳細分析博文,參見文獻[4],寫的很不錯。

 

【1】S Mallat, Z Zhang. Matchingpursuit with time-frequency dictionaries[J]. IEEE Transactions on SignalProcessing, 1993, 41(12): 3397-3415.

【2】了凡春秋. Matlab匹配追蹤(Matching Pursuit) 之一,https://chunqiu.blog.ustc.edu.cn/

【3】了凡春秋. Matlab匹配追蹤(Matching Pursuit) 之二,https://chunqiu.blog.ustc.edu.cn/

【4】逍遙劍客. MP算法和OMP算法及其思想,http://blog.csdn.NET/scucj/article/details/7467955

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章