如何使用PHP计算图像的2D DCT?

3
我正在尝试使用PHP查找一张图片的2D DCT(离散余弦变换)。我已经使用下面的公式来查找它。 enter image description here 其中,x和y是图片中像素的坐标,N是图像的长度和宽度。C(u)和C(v)是常数,其值可以通过下面的公式计算: enter image description here 对于u和v的值从0到N-1,上述公式将产生一组不同的C(u)和C(v)值。
以下是我用来查找DCT的代码。
function getGray($img,$x,$y){
    $col = imagecolorsforindex($img, imagecolorat($img,$x,$y));
    return intval($col['red']*0.3 + $col['green']*0.59 + $col['blue']*0.11);
}

function  initCoefficients() {
  for ($i=1;$i<$this->size;$i++) 
    {
    $c[$i]=1;
    }
    $c[0]=1/sqrt(2.0);
return $c;
}

function applyDCT($imagePath) {
    $img = $this->readImageTo($imagePath, 32, 32);
    $color=array();

    for($i=0;$i<32;$i++)
    {
        for($j=0;$j<32;$j++)
        {
            $color[]=$this->getGray($img,$i,$j);
        }
    }

    $N=32;


    $c=$this->initCoefficients();
    $sum=0;
    for ($u=0;$u<$N;$u++) {
    for ($v=0;$v<$N;$v++) {

        for ($i=0;$i<$N;$i++) {
            for ($j=0;$j<$N;$j++) {
                $sum += ($c[$i]*$c[$j])*cos(((2*$i+1)*$u*pi()/(2.0*$N)))*cos(((2*$j+1)*$v*pi()/(2.0*$N)))*($color[$i][$j]);
          }
        }

        $sum *=sqrt(2/$N)*sqrt(2/$N);
        $F[$u][$v] = $sum;
      }
    }
    return $F;
}

图像大小为32*32。我的问题是,一旦我调用applyDCT()函数,它会给出一个数组,其中所有元素的值都为0。
例如:

数组([0] => 数组(...,3 => 0 [4] => 0 [5] => 0,...

我认为问题在于我的计算。我做错了什么?请帮帮我,谢谢。

第二个循环中应该使用$M而不是$N,还有sqrt(2/$N);的正确写法吗? - viral
$M和$N的大小相同(32)。所以,我希望这不是一个问题。 - Tharu
$color不太对。你在1D中初始化它,但在数学运算中却像2D数组一样调用它。 在你的数学运算中,将$color[$i][$j]替换为$color[$i*32+$j],我想这样应该可以解决问题... 或者确保你的$color数组形成符合你期望的方式,也许通过应用var_dump()函数来检查。 - niconoe
我把applyDCT函数中的$color[]=$this->getGray($img,$i,$j)改成了$color[$i][$j]=$this->getGray($img,$i,$j),现在它给出了一些值。你为什么要建议用$color[$i*32+$j]替换$color[$i][$j]进行数学运算?现在我还需要这样做吗? - Tharu
不需要了,这个技巧只适用于您计划将$color保留为一维数组的情况。 $i * 32 + $j是从2D转换为1D数字索引数组的技巧(当前行* nb列+当前列),但是您现在不再需要它,因为您的$color现在是一个2D数组;)。您是否希望我提供答案,以便您可以接受并解决您的问题?祝好! - niconoe
@niconoe 谢谢。我明白了。 - Tharu
1个回答

1

以下是基于评论的答案:

$color不好。你在1D中初始化它,但在数学运算中却像它是一个2D数组一样调用它。在你的数学运算中,将$color[$i][$j]替换为$color[$i*32+$j],我想应该可以解决问题...或者确保你的$color数组形成符合你的预期。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接