2010年5月25日 星期二

Compressive Sensing (matlab code using DCT)

clc;clear
load DCTq;  %讀量化表格
% Read the input image;           
xtatal = double(imread('lena512.bmp')); %讀圖檔 目前應該是黑白
figure(1);
imshow(uint8(xtatal));  %秀出原始圖檔
% keep an original copy of the input signal
for i=0:size(xtatal,1)/8-1                  %每格寬8像素 總共 (寬/8) 格 需整除
    for j=0:size(xtatal,1)/8-1              %每格高8像素 總共 (高/8) 格 需整除
        x0 = xtatal(1+i*8:8+i*8,1+j*8:8+j*8);       %一個block 處理
%         xmean = mean(x0(:));
%         x0=x0-xmean;
        % figure(1);
        % imshow(uint8(x0));
        f=floor((dct2(x0)+floor(Q/2))./Q);      %一個block作DCT和量化後的 係數(稀疏)
        f = f(:);                               %拉成一維 (n*1)
        n= size(x0,1)*size(x0,1);               %總點數 n

        s=length(find(floor((dct2(x0)+floor(Q/2))./Q)~=0)); %不等於0的有s個
       
        M=32;                                           %設定M大小 每個block 都用一樣
%         M=s*log(n/s)+1;                               %需大於s*log(n/s) 公式?
%         if (M<32)                                     %補不足的點(自己設定的)
%             M=32;
%         end

        A = get_A_random(n,M);          %sensing matrix (M*n)
        Psi=dctmtx(n);                  %DCT基底 (n*n)
        y = A*Psi*f;                    %measurment (壓縮後大小 y(M*1)) (編碼)

        %用(l1 magic)tool 求l1 最佳稀疏解 (解碼)
%         % S o l v e u s ing l 1 magic .
%         path(path ,'./Optimization') ;
%         xinit = pinv(A)*y; % i n i t i a l g u e s s = min ene r g y
%         tic
%         xp = l1eq_pd ( xinit , A, [ ] , y , 1e-3);
%         toc

        %用CVX tool 求l1 最佳稀疏解 (解碼)
        cvx_begin
            variable xp(n);
            minimize (norm( xp , 1 ) ) ;
            subject to
                A*Psi*xp == y ;
        cvx_end
       
        %norm(f-xp)/norm(f);        %計算誤差??
        hat_x=reshape(round(xp),8,8);       %(n*1)一維轉換成8*8
        xhatall(1+i*8:8+i*8,1+j*8:8+j*8)=(idct2(floor(hat_x.*Q)));  %反量化&反DCT 還原圖檔
       
        %調整超過的像素值
        [r1,c1]=(find(xhatall>255));
        for l=1:length(r1)
            xhatall(r1(l),c1(l))=255;
        end
        [r2,c2]=(find(xhatall<0));
        for l=1:length(r2)
            xhatall(r2(l),c2(l))=0;
        end

        %不確定對不對的方式
%         xhatall(1+i*8:8+i*8,1+j*8:8+j*8)=reshape(Psi*reshape(hat_x.*Q,64,1),8,8);
    end
end

figure(2);
imshow(uint8(xhatall));     %秀出還原的圖檔

3 則留言:

小鍾 提到...

小弟我有些問題想請教

首先 Q 哪邊來的??
get_A_random 這函式是您自己寫的嗎??

老實說 我有拿您的code 去 compiler過
發現有些地方有錯

不好意思 我問的問題有些愚笨
因為小弟我是新手
最近剛好正在研究CS

Lee 提到...

抱歉ˇˇ

想說沒人會看 就很少來看@@
Q是DCT的量化矩陣

get_A_random如下
function A =get_A_random (n,m)
A = sqrt(1/m)*randn(m,n);
end

Unknown 提到...

小弟我也有些問題想請教

我想問Q量化的table有程式碼可以讀嗎?

我也是最近在看CS
想說來問問