双线性插值resize实现图片放缩

双线性插值resize实现图片放缩

opencv的resize的双线性插值实现
简简单单两张图说明原理,仔细看一会原理就懂了,不要怕图二的数学公式,看明白就知道有多简单了。
在这里插入图片描述
在这里插入图片描述
原理看懂了的话,就来看实现吧。
这里实现的重点是要以两张图片的中心建立坐标系,进行计算。
黑点为坐标原点
图中黑点即为坐标原点,第一种在进行图片放缩时是错误的做法,正确做法第二种,以中心为坐标原点进行计算,并且需要注意一点的是,**当你用将浮点数截断转整,在不同的象限求x1,x2,y1,y2所做的操作是不同的。**例如 -3.5得到的是-3和-4 ,是x的x-1的值,而3.5得到的是3和4,是x和x+1的值。
附上我的代码

void resize(int srcH, int srcW, int dstH, int dstW, uchar src[], uchar dst[]) {
    
    
	int ox = (srcW - 1) / 2.0;
	int oy = (srcH - 1) / 2.0;
	float sx = ox * 2.0 / dstW;
	float sy = oy * 2.0 / dstH;
	for (int i = 0; i < dstH; i++) {
    
    
		for (int j = 0; j < dstW; j++) {
    
    
			float rx = 1.0* j * sx - ox;
			float ry = 1.0*i * sy - oy;
			int x = rx;
			int y = ry;
			float q = 0;
			int y1 = y + oy > srcH ? srcH : y + oy; y1 = y1 < 0 ? 0 : y1;
			int y2 = y + oy + (y > 0 ? 1 : -1) > srcH ? srcH : y + oy + (y > 0 ? 1 : -1); y1 = y1 < 0 ? 0 : y1;
			int x1 = x + ox > srcW ? srcW : x + ox; x1 = x1 < 0 ? 0 : x1;
			int x2 = x + ox + (x > 0 ? 1 : -1) > srcW ? srcW : x + ox + (x > 0 ? 1 : -1); x2 = x2 < 0 ? 0 : x2;
			float q1 = (x > 0 ? 1 : -1)*(x + (x > 0 ? 1 : -1) - rx)*src[y1*srcW + x1] + (x > 0 ? 1 : -1)*(rx - x)*src[y1*srcW + x2];
			float q2 = (x > 0 ? 1 : -1)*(x + (x > 0 ? 1 : -1) - rx)*src[y2*srcW + x1] + (x > 0 ? 1 : -1)*(rx - x)*src[y2*srcW + x2];
			q = (y > 0 ? 1 : -1)*(y + (y > 0 ? 1 : -1) - ry)*q1 + (y > 0 ? 1 : -1)*(ry - y)*q2;
			//cout << rx << "\t" << ry << endl;
			dst[i*dstW + j] = q;

		}
	}
}

请原谅我这鬼畜之极的代码,太晚了,懒得改了(我也不知道为什么会写成这样),对了,我偷懒了一点,使得边界会有像素损失。

猜你喜欢

转载自blog.csdn.net/weixin_45275421/article/details/109126608