急求高人指点啊,哪里出问题了,为什么我在Matlab里就运行不了

时间:2022-04-26 17:41:36
function [y]=invZigzag(x)
% inverse transform from the zigzag format to the matrix form

row=round(sqrt(length(x)));

if row*row~=length(x)
   disp('invZigzag() fails!! Must be a square matrix!!');
   return;
end;

y=zeros(row,row);
count=1;
for s=1:row
   if mod(s,2)==0
      for m=s:-1:1
         y(m,s+1-m)=x(count); 
         count=count+1;
      end;
   else 
      for m=1:s
         y(m,s+1-m)=x(count); 
         count=count+1;
      end;
   end;
end;

if mod(row,2)==0
   flip=1;
else
   flip=0;
end;

for s=row+1:2*row-1
   if mod(flip,2)==0
      for m=row:-1:s+1-row
         y(m,s+1-m)=x(count); 
         count=count+1;
      end;
   else 
      for m=row:-1:s+1-row
         y(s+1-m,m)=x(count);
         count=count+1;
      end;
   end;
   flip=flip+1;
end;
b = imread('D:\matlab\toolbox\images\imdemos\Lena.bmp');
b = im2uint8(b);
figure(1);imshow(b);% 显示原始图像
b = double(b);


b_temp = b-128;
m = size(b_temp,1);n = size(b_temp,2);

%% 离散余弦变换DCT
b_DCT = zeros(m,n);
% 初始化DCT矩阵,便于计算
N = 8;
DCT_matrix = zeros(N,N);
for k = 1:N
    for l = 1:N
        DCT_matrix(k,l) = cos((2*(k-1)+1)*(l-1)*pi/(2*N));
    end
end
% 将原始图像分块(NXN)并进行DCT变换
for k = 1:m/N
    for l = 1:n/N
        x1 = 1+N*(k-1);x2 = N*k;y1 = 1+N*(l-1);y2 = N*l;
        b_DCT(x1:x2,y1:y2) = my_dct2(b_temp(x1:x2,y1:y2),DCT_matrix,N);
    end
end

%% 量化
b_Q = zeros(m,n);
% 初始化量化矩阵(低频部分量化系数小,高频部分量化系数大),滤去更多高频信息
Q_matrix = zeros(N,N);Q11 = 4;step = 3;
for k = 1:N
    for l = 1:N
        Q_matrix(k,l) = Q11+step*(k-1)+step*(l-1);
    end
end
% 将DCT后的矩阵进行量化并去整
for k = 1:m/N
    for l = 1:n/N
        x1 = 1+N*(k-1);x2 = N*k;y1 = 1+N*(l-1);y2 = N*l;
        b_Q(x1:x2,y1:y2) = round(b_DCT(x1:x2,y1:y2)./Q_matrix);% 点除
    end
end

%% 编码
% % 构建zigzag变换表(可以快速实现变换),注意仅适用于8X8矩阵
% zigzag = [ 0, 1, 8, 16, 9, 2, 3, 10, ...
%     17, 24, 32, 25, 18, 11, 4, 5, ...
%     12, 19, 26, 33, 40, 48, 41, 34, ...
%     27, 20, 13, 6, 7, 14, 21, 28, ...
%     35, 42, 49, 56, 57, 50, 43, 36, ...
%     29, 22, 15, 23, 30, 37, 44, 51, ...
%     58, 59, 52, 45, 38, 31, 39, 46, ...
%     53, 60, 61, 54, 47, 55, 62, 63];
% zigzag = zigzag+1;

b_encode = zeros(m,n);number = 0;j = 0;
for k = 1:m/N
    for l = 1:n/N
        x1 = 1+N*(k-1);x2 = N*k;y1 = 1+N*(l-1);y2 = N*l;
        % 将8X8矩阵zig-zag变换生成1X64数组,使连续的零个数最多
%         B = reshape(b_Q(x1:x2,y1:y2),1,N*N); 
%         B_encode = B(zigzag); 
        B_encode = toZigzag(b_Q(x1:x2,y1:y2));
 
        % 游程编码
        for i = 1:N*N
            if B_encode(i)~=0
                % 第一个字节存储下一个非零值与上一个非零值之间0的个数
                byte1 = uint8(j);% 使用无符号8位整型
%                 byte1 = bitshift(uint8(j),4);
%                 byte1 = byte1+uint8(1);
                % 第二个字节存储下一个非零值
                byte2 = int8(B_encode(i));% 使用有符号8位整型
                b_encode(number+1) = byte1;
                b_encode(number+2) = byte2;
                j = 0;number = number+2;
            else
                j = j+1;
            end
        end
        
    end
end

b_encode = b_encode(1:number);% 压缩后的数据

%% 计算压缩比
code_bits = number*8;% 压缩数据大小(比特)
origin_bits = m*n*8;% 源数据大小(比特)
compression_ratio = origin_bits/code_bits;% 压缩比
disp('压缩比:');disp(compression_ratio);
function [B] = my_dct2(A,DCT_matrix,N)
%dct2主函数,使用于NXN矩阵
if (size(A,1)~=N)||(size(A,2)~=N)
    error('矩阵A阶数错误');
end

B = zeros(N,N);
for k = 1:N
    for l = 1:N
        b_temp = 0;
        for m = 1:N
            for n = 1:N
                b_temp = b_temp+A(m,n)*DCT_matrix(m,k)*DCT_matrix(n,l);
            end
        end
        
        if k ~= 1
            c_u = 1;
        else
            c_u = 1/sqrt(2);
        end
        if l ~= 1;
            c_v = 1;
        else
            c_v = 1/sqrt(2);
        end

        B(k,l) = 1/4*c_u*c_v*b_temp;
        
    end
end
%% 解码
% % 反zigzag变换表
% [temp,izigzag] = sort(zigzag);

% 反游程编码
b_decode = zeros(1,m*n);number = 0;
for i = 1:2:size(b_encode,2)
    b_decode(number+1:number+b_encode(i)) = 0;%zeros(1,b_encode(i));
    b_decode(number+1+b_encode(i)) = b_encode(i+1);
    number = number+b_encode(i)+1;
end

% 反zig-zag变换
b_decode2 = zeros(m,n);
for k = 1:m/N
    for l = 1:n/N
        x1 = 1+N*(k-1);x2 = N*k;y1 = 1+N*(l-1);y2 = N*l;
        start = N*N*((k-1)*n/N+(l-1))+1;
%         temp = b_decode(start:start+63);
%         b_decode2(x1:x2,y1:y2) = reshape(temp(izigzag),N,N);
        b_decode2(x1:x2,y1:y2) = invZigzag(b_decode(start:start+N*N-1));
    end
end

%% 量化逆
b_deQ = zeros(m,n);
for k = 1:m/N
    for l = 1:n/N
        x1 = 1+N*(k-1);x2 = N*k;y1 = 1+N*(l-1);y2 = N*l;
        b_deQ(x1:x2,y1:y2) = b_decode2(x1:x2,y1:y2).*Q_matrix;
    end
end

%% 逆DCT
b_IDCT = zeros(m,n);
for k = 1:m/N
    for l = 1:n/N
        x1 = 1+N*(k-1);x2 = N*k;y1 = 1+N*(l-1);y2 = N*l;
        b_IDCT(x1:x2,y1:y2) = my_idct2(b_deQ(x1:x2,y1:y2),DCT_matrix,N);
    end
end

%% 显示
b_show = uint8(b_IDCT+128);
%b_show = mat2gray(b_show);
figure(2);imshow(b_show);

imwrite(b_show,'Lena2.bmp','bmp');

%% 计算PSNR
psnrvalue = PSNR('Lena.bmp','Lena2.bmp');
disp('峰值信噪比:');disp(psnrvalue);
function [B] = my_dct2(A,DCT_matrix,N)
%dct2主函数,使用于NXN矩阵
if (size(A,1)~=N)||(size(A,2)~=N)
    error('矩阵A阶数错误');
end

B = zeros(N,N);
for k = 1:N
    for l = 1:N
        b_temp = 0;
        for m = 1:N
            for n = 1:N
                b_temp = b_temp+A(m,n)*DCT_matrix(m,k)*DCT_matrix(n,l);
            end
        end
        
        if k ~= 1
            c_u = 1;
        else
            c_u = 1/sqrt(2);
        end
        if l ~= 1;
            c_v = 1;
        else
            c_v = 1/sqrt(2);
        end

        B(k,l) = 1/4*c_u*c_v*b_temp;
        
    end
end
function [B] = my_idct2(A,DCT_matrix,N)
%idct2主函数,使用于NXN矩阵
if (size(A,1)~=N)||(size(A,2)~=N)
    error('矩阵A阶数错误');
end

B = zeros(N,N);
for k = 1:N
    for l = 1:N
        b_temp = 0;
        for m = 1:N
            for n = 1:N
                
                if m ~= 1
                    c_u = 1;
                else
                    c_u = 1/sqrt(2);
                end
                if n ~= 1;
                    c_v = 1;
                else
                    c_v = 1/sqrt(2);
                end
                
                b_temp = b_temp+c_u*c_v*A(m,n)*DCT_matrix(k,m)*DCT_matrix(l,n);
            end
        end
        
        B(k,l) = 1/4*b_temp;
        
    end
end
function psnrvalue = PSNR(original,unzip)
%% 计算原始图像的信号功率
A = imread(original);
A = double(A);
B = imread(unzip);
B = double(B);

%% 计算MSE

[m,n] = size(A);
[m1,n1] = size(B);
if m~=m1||n~=n1
    error('图像大小不一致');
end

msevalue = 0;
for i = 1:m
    for j = 1:n
        msevalue = msevalue+(A(i,j)-B(i,j))^2;
    end
end
msevalue = msevalue/(m*n);
if msevalue == 0
    error('图像完全相同');
end

%% 计算峰值信噪比
psnrvalue = 255^2/msevalue;
psnrvalue = 10*log10(psnrvalue);
function [y]=toZigzag(x)
% transform a matrix to the zigzag format

[row col]=size(x);

if row~=col
   disp('toZigzag() fails!! Must be a square matrix!!');
   return
end

y=zeros(row*col,1);
count=1;
for s=1:row
   if mod(s,2)==0
      for m=s:-1:1
         y(count)=x(m,s+1-m); 
         count=count+1;
      end;
   else 
      for m=1:s
         y(count)=x(m,s+1-m);
         count=count+1;
      end
   end
end

if mod(row,2)==0
   flip=1;
else
   flip=0;
end

for s=row+1:2*row-1
   if mod(flip,2)==0
      for m=row:-1:s+1-row
         y(count)=x(m,s+1-m); 
         count=count+1;
      end
   else 
      for m=row:-1:s+1-row
         y(count)=x(s+1-m,m);
         count=count+1;
      end;
   end;
   flip=flip+1;
end

2 个解决方案

#1


这么长又不说什么错误

#2


发错位置了,这里是C语言板块啊

#1


这么长又不说什么错误

#2


发错位置了,这里是C语言板块啊