使用1D DCT进行2D离散余弦变换

umpk_sync

我正在尝试通过使用1D DCT操作将2D离散余弦变换实现为图像。如果将其与dct2MATLAB函数进行比较,则输出不正确我不明白我的代码出了什么问题以及它在哪里发生。

如果有人可以指出错误或任何其他建议,那将非常有帮助。

这是我用MATLAB写的代码

% main function
signal=rand(100);
signal_dct=myDCT(signal);
figure; imshow((signal_dct));

% function to calculate 2D DCT of an image
function res=myDCT(signal)

    signal=double(signal);

    l=size(signal,1);

    res=zeros(l);  %initialize the final result matrix

    for k=1:l     %calculate 1D DCT of each row of image
        res(k,:)=mdct(signal(k,:));  
    end

    for k=1:l   %calculate 1D DCT of each column of image
        res(:,k)=mdct(res(:,k));
    end
end

%% function to calculate 1D DFT of a 1D signal
function res=mdct(signal)

    l=size(signal,1);

    for i=1:l

        if i==1   %for signal index of 1, alpha is 1/sqrt(l)
            alpha=sqrt(1/l);
        else   %for signal index of greater than 1
            alpha=sqrt(2/l);
        end

        j=[1:l];
        % summation calculates single entry of res by applying the  
        % formula of DCT on the signal
        summation=sum(sum(signal(j)*cos((pi*(2*(j-1)+1)*(i-1))/(2*l))));
        res(i)=alpha*summation;        
    end
end
雷瑞恩

您是正确的,因为2D DCT是可分离的。您只需先将1D DCT应用于每一行,然后获取中间结果并将其应用于列。但是,您有两个基本错误。让我们来看看它们。

错误1-DCT的大小不正确

具体来说,请在mdct函数中查看以下语句

l=size(signal,1);

因为你申请了DCT的每一行,然后每列,上面只会工作,如果你申请了DCT的如果输入是一列,size(signal,1)肯定会给你输入向量的长度但是,如果你输入了一个,然后输出将是1因此,应替换,以确保获得元素总数-不管输入是行还是列。size(signal,1)size(signal,1)numel

另外,如果您想使代码兼容以进行DCT循环中的求和,则无论输入如何,都应确保输入是行向量因此,请执行以下操作:

l = numel(signal);
signal = signal(:).';

第一行确定输入信号有多少个元素,第二行确保有行向量。这是通过(:)将元素展开到列向量中来完成的,然后执行以下操作.'以确保我们将结果转置为行向量。

错误2-求和语句不正确

接下来,您将必须在求和中进行逐元素乘法才能获得所需的内容。您也不需要sum那里的额外电话。这是多余的。因此,将汇总语句修改为此:

summation=sum(signal.*cos((pi*(2*(j-1)+1).*(i-1))/(2*l)));

不需要这样做,signal(j)因为它j跨越了向量的整个长度,您可以使用来做到这一点signal


一旦进行了这些更改,就在较小的矩阵上进行了此操作,以确保获得相同的结果:

rng(123123);
signal=rand(7);
signal_dct=myDCT(signal);
signal_dct2 = dct2(signal);

最后一行代码调用,dct2以便我们可以比较自定义函数的结果以及dct2提供给我们的结果。

我们得到:

>> signal_dct

signal_dct =

    3.7455   -0.1854   -0.1552    0.3949    0.2182   -0.3707    0.2621
   -0.2747    0.1566   -0.0955    0.1415    0.3156   -0.0503    0.8581
   -0.2095    0.0233   -0.2769   -0.4341   -0.1639    0.3700   -0.2282
   -0.0282    0.0791    0.0517    0.4749   -0.0169   -0.4327    0.0427
   -0.4047   -0.4383    0.3415   -0.1120   -0.0229    0.0310    0.3767
   -0.6058   -0.0389   -0.3460    0.2732   -0.2395   -0.2961    0.1789
   -0.0648   -0.3173   -0.0584   -0.3461   -0.1866    0.0301    0.2710

>> signal_dct2

signal_dct2 =

    3.7455   -0.1854   -0.1552    0.3949    0.2182   -0.3707    0.2621
   -0.2747    0.1566   -0.0955    0.1415    0.3156   -0.0503    0.8581
   -0.2095    0.0233   -0.2769   -0.4341   -0.1639    0.3700   -0.2282
   -0.0282    0.0791    0.0517    0.4749   -0.0169   -0.4327    0.0427
   -0.4047   -0.4383    0.3415   -0.1120   -0.0229    0.0310    0.3767
   -0.6058   -0.0389   -0.3460    0.2732   -0.2395   -0.2961    0.1789
   -0.0648   -0.3173   -0.0584   -0.3461   -0.1866    0.0301    0.2710

如您所见,两个结果都匹配。对我来说看上去很好!


为了确保我们保持一致,这是您的两个函数的完整代码清单,其中包括我所做的修改:

% function to calculate 2D DCT of an image
function res=myDCT(signal)

    signal=double(signal);

    l=size(signal,1);

    res = zeros(l);

    for k=1:l     %calculate 1D DCT of each row of image
        res(k,:)=mdct(signal(k,:));  
    end

    for k=1:l   %calculate 1D DCT of each column of image
        res(:,k)=mdct(res(:,k));
    end
end

%% function to calculate 1D DFT of a 1D signal
function res=mdct(signal)

    %// Change
    l = numel(signal);
    signal = signal(:).';

    for i=1:l

        if i==1   %for signal index of 1, alpha is 1/sqrt(l)
            alpha=sqrt(1/l);
        else   %for signal index of greater than 1
            alpha=sqrt(2/l);
        end

        j=[1:l];
        % summation calculates single entry of res by applying the  
        % formula of DCT on the signal
        %// Change
        summation=sum(signal.*cos((pi*(2*(j-1)+1).*(i-1))/(2*l)));
        res(i)=alpha*summation;        
    end
end

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章

来自分类Dev

在Python中实现2D离散余弦变换的问题

来自分类Dev

MATLAB中的2D离散傅立叶变换实现

来自分类Dev

Matlab:2D离散傅立叶变换和逆

来自分类Dev

MATLAB中的2D离散傅立叶变换实现

来自分类Dev

Matlab/Octave 2D 离散傅立叶变换

来自分类Dev

使用python查找正向和反向离散余弦变换。请不要使用numpy内置的dct和idct

来自分类Dev

图像的离散余弦变换(DCT)

来自分类Dev

如何对1d和2d数组强制使用2d形状

来自分类Dev

使用PIL将1D Numpy Array转换为1D图像

来自分类Dev

Java中的离散余弦变换(DCT)

来自分类Dev

离散余弦变换(DCT)系数分布

来自分类Dev

如何使用if条件在1D和2D numpy数组之间进行向量化计算

来自分类Dev

使用1D X,Y和Z变量在python中进行2D等高线图

来自分类Dev

使用边界条件浏览映射到1D的2D数组

来自分类Dev

使用OpenGL矩阵转换将纹理从“ 1D”映射到“ 2D”

来自分类Dev

如何使用numpy从两个1D数组生成布尔2D数组

来自分类Dev

使用曲折排序将1d转换为2d矩阵

来自分类Dev

使用1d张量将Tensorflow索引为2d张量

来自分类Dev

使用指针时将2D数组用作多个1D数组

来自分类Dev

使用2D数组中的值索引1D数组

来自分类Dev

使用循环从1D数组创建2D数组(JavaScript)

来自分类Dev

如何在1D数组上使用函数创建2D Numpy数组?

来自分类Dev

如何使用1d数组中的值填充2d数组?

来自分类Dev

是否可以使用1D索引访问C ++ 2D int数组?

来自分类Dev

使用步骤迭代1D数组和2D数组

来自分类Dev

使用1D FFT与2D FFT的可分卷积

来自分类Dev

使用指针时将2D数组用作多个1D数组

来自分类Dev

在C ++中使用1D数组初始化2D数组

来自分类Dev

使用foreach在PHP中将2d数组乘以1d数组

Related 相关文章

热门标签

归档