三线性插值

效果并不理想,在图像梯度大的地方很容易出现噪声干扰。
运行时间很长,时效性差

void Cimage2View::ThreeLinearInterpolation(unsigned char** SourceData, int Width , int Height , int Band , 
                            unsigned char** NewData, int NewWidth , int NewHeight , float Scale)
{
    /*
    f(i+u,j+v) = [A] * [B] * [C]
    [A]=[ S(u + 1) S(u + 0) S(u - 1) S(u - 2) ]
    ┏ f(i-1, j-1) f(i-1, j+0) f(i-1, j+1) f(i-1, j+2) ┓
    [B]=┃ f(i+0, j-1) f(i+0, j+0) f(i+0, j+1) f(i+0, j+2) ┃
    ┃ f(i+1, j-1) f(i+1, j+0) f(i+1, j+1) f(i+1, j+2) ┃
    ┗ f(i+2, j-1) f(i+2, j+0) f(i+2, j+1) f(i+2, j+2) ┛
    ┏ S(v + 1) ┓
    [C]=┃ S(v + 0) ┃
    ┃ S(v - 1) ┃
    ┗ S(v - 2) ┛
     ┏ 1-2*Abs(x)^2+Abs(x)^3      , 0<=Abs(x)<1
    S(x)={ 4-8*Abs(x)+5*Abs(x)^2-Abs(x)^3 , 1<=Abs(x)<2
     ┗ 0                , Abs(x)>=2
    S(x)是对 Sin(x*Pi)/x 的逼近(Pi是圆周率——π)
    */
    //(x0,y0)为目标文件按比例缩放之后的点
    float x0;
    float y0;
    //左上角的点(x1,y1)
    int x1;
    int y1;
    //与左上角点的浮点差值
    float u ;
    float v;
    //保存计算的中间变量
    float temp[4];

    for(int b = 0;b < Band;++b)
    {
        for(int x = 0;x < NewHeight;++x)
        {
            for(int y = 0;y < NewWidth;++y)
            {
                x0 = x / Scale;
                y0 = y / Scale;

                x1 = int(x0);
                y1 = int(y0);

                u = x0 - x1;
                v = y0 - y1;

                if((x1 - 1) < 0 || (y1 - 1) < 0 || (x1 + 3) > Height || (y1 + 3) > Width)
                    continue;

                temp[0] = SourceData[b][(x1 - 1) * Width + (y1 - 1)] * S(u + 1)
                        + SourceData[b][x1 * Width + (y1 - 1)] * S(u)
                        + SourceData[b][(x1 + 1) * Width + (y1 - 1)] * S(u - 1)
                        + SourceData[b][(x1 + 2) * Width + (y1 - 1)] * S(u - 2);

                temp[1] = SourceData[b][(x1 - 1) * Width + y1] * S(u + 1)
                        + SourceData[b][x1 * Width + y1] * S(u)
                        + SourceData[b][(x1 + 1) * Width + y1] * S(u - 1)
                        + SourceData[b][(x1 + 2) * Width + y1] * S(u - 2);

                temp[2] = SourceData[b][(x1 - 1) * Width + (y1 + 1)] * S(u + 1)
                        + SourceData[b][x1 * Width + (y1 + 1)] * S(u)
                        + SourceData[b][(x1 + 1) * Width + (y1 + 1)] * S(u - 1)
                        + SourceData[b][(x1 + 2) * Width + (y1 + 1)] * S(u - 2);

                temp[3] = SourceData[b][(x1 - 1) * Width + (y1 + 2)] * S(u + 1)
                        + SourceData[b][x1 * Width + (y1 + 2)] * S(u)
                        + SourceData[b][(x1 + 1) * Width + (y1 + 2)] * S(u - 1)
                        + SourceData[b][(x1 + 2) * Width + (y1 + 2)] * S(u - 2);

                NewData[b][x * NewWidth + y] = temp[0] * S(v + 1) + temp[1] * S(v)
                                                + temp[2] * S(v - 1) + temp[3] * S(v - 2);
            }
        }
    }
}



//S(x)是对 Sin(x*Pi)/x 的逼近(Pi是圆周率——π)
float Cimage2View::S(float x)
{
    float returnValue;

    if(abs(x) >= 0 && abs(x) < 1)
        returnValue = 1 - 2 * abs(x) * abs(x) + abs(x) * abs(x) * abs(x);
    else if(abs(x) >= 1 && abs(x) < 2)
        returnValue = 4 - 8 * abs(x) + 5 * abs(x) * abs(x) - abs(x) * abs(x) * abs(x);
    else if(abs(x) >= 2)
        returnValue = 0;
    else
    {
        MessageBox("S(x)输入有误");
    }
    return returnValue;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值