陕西建设监理协会网站,河北省住房和建设厅网站首页,网站主机免备案,小辣椒网站开发图像的简单几何变换
先看一下关于图像几何变换的简介#xff1a;
几何变换不改变图像的像素值#xff0c;只是在图像平面上进行像素的重新安排。
适当的几何变换可以最大程度地消除由于成像角度、透视关系乃至镜头自身原因所造成的几何失真所产生的负面影响。有利于我们在后续…图像的简单几何变换
先看一下关于图像几何变换的简介
几何变换不改变图像的像素值只是在图像平面上进行像素的重新安排。
适当的几何变换可以最大程度地消除由于成像角度、透视关系乃至镜头自身原因所造成的几何失真所产生的负面影响。有利于我们在后续的处理和识别工作中将注意力集中子图像内容本身更确切地说是图像中的对象而不是该对象的角度和位置等。几何变换常常作为图像处理应用的预处理步骤是图像归一化的核心工作之一。
一个几何变换需要两部分运算首先是空间变换所需的运算如平移、缩放、旋转和正平行投影等需要用它来表示输出图像与输入图像之间的像素映射关系此外还需要使用灰度差值算法因为按照这种变换关系进行计算输出图像的像素可能被映射到输入图像的非整数坐标上。
一图形的平移
对于图像的平移非常简单在平移之前我们需要先构造一个移动矩阵所谓移动矩阵就是让说明白在x轴方向上移动多少距离在y轴上移动多少距离。
通过numpy来构造这个矩阵并将其传给仿射函数cv2.warpAffine( )
仿射函数cv2.warpAffine( 接受三个参数需要进行图像变换的原始图像矩阵移动矩阵以及图像变换的大小这里要说明一下图像本身并不会放大或缩小而是图像显示区域的大小
img cv2.imread(4.jpg)
# 构造移动矩阵H
# 在x轴方向移动多少距离在y轴方向移动多少距离
H np.float32([[1, 0, 50], [0, 1, 25]])
rows, cols img.shape[:2]
print(img.shape)
print(rows, cols)
res cv2.warpAffine(img, H, (cols, rows)) # 注意这里rows和cols需要反置个人感觉这里是一个坑
cv2.imshow(origin_picture, img)
cv2.imshow(new_picture, res)
cv2.waitKey(0)二图像的放大和缩小
图像的放大和缩小有一个专门的函数就是cv2.resize( )这其中就需要设置缩放的比例一种办法是设置缩放因子另一种办法是直接设置图像的大小在缩放以后图像必然会发生变化这就涉及到图像的插值问题。
缩放有几种不同的插值interpolation方法在缩小时推荐使用cv2.INTER_AREA扩大时推荐使用cv2.INTER_CUBIC和cv2.INTER_LINEAR。
img cv2.imread(4.jpg)
# 一是通过设置图像缩放比例即缩放因子来对图像进行放大或缩小
res1 cv2.resize(img, None, fx2, fy2, interpolationcv2.INTER_LINEAR)
height, width img.shape[:2]
# 二是直接设置图像的大小不需要缩放因子
res2 cv2.resize(img, (int(0.8*width), int(0.8*height)), interpolationcv2.INTER_AREA)
cv2.imshow(origin_picture, img)
cv2.imshow(res1, res1)
cv2.imshow(res2, res2)
cv2.waitKey(0)关于插值算法有很多我这里举一个例子。
最近邻插值算法选择离它映射到的位置最近的输入像素的灰度值为插值结果。
通过图像长和宽的比例将原有的图像映射到所需要的图像上。这里涉及到对图像矩阵元素的操作对于其如何计算的可以看代码也可以联系我从数学的角度解释。
# need_height参数不得超过原来图像高的两倍这是由临近插值算法本身的性质所决定的
# need_width参数则可以任意选取
def pic_interpolation(img, need_height, need_width):height, width, channels img.shapeprint(height, width, channels)emptyImage np.zeros((need_height, need_width, channels), np.uint8)sh need_height/heightsw need_width/widthfor i in range(need_height):for j in range(need_width):x round(i/sh)y math.floor(j/sw)emptyImage[i, j] img[x, y]return emptyImageimg cv2.imread(4.jpg)
zoom pic_interpolation(img, 220, 180)
cv2.imshow(nearest neighbor, zoom)
cv2.imshow(image, img)
cv2.waitKey(0)三图像的旋转
对于图像的旋转我们需要构造旋转矩阵。一般的图像的旋转矩阵是在原点处进行变换的为了能够在任意位置进行旋转变换OpenCV采用了另一种方式为了构造这个矩阵OpenCV提供了一个函数cv2.getRotationMarix2D( )这个函数需要三个参数旋转中心旋转角度旋转后图像的缩放比例
img cv2.imread(4.jpg)
rows, cols img.shape[:2]
# 第一个参数是旋转中心第二个参数是旋转角度第三个参数是缩放比例
M1 cv2.getRotationMatrix2D((cols/2, rows/2), 45, 0.5)
M2 cv2.getRotationMatrix2D((cols/2, rows/2), 45, 2)
M3 cv2.getRotationMatrix2D((cols/2, rows/2), 45, 1)
res1 cv2.warpAffine(img, M1, (cols, rows))
res2 cv2.warpAffine(img, M2, (cols, rows))
res3 cv2.warpAffine(img, M3, (cols, rows))
cv2.imshow(res1, res1)
cv2.imshow(res2, res2)
cv2.imshow(res3, res3)
cv2.waitKey(0)
cv2.destroyAllWindows()四图像的仿射
仿射变换是指在向量空间中进行一次线性变换(乘以一个矩阵)并加上一个平移(加上一个向量)变换为另一个向量空间的过程。
Affine Transform描述了一种二维仿射变换的功能它是一种二维坐标之间的线性变换保持二维图形的“平直性”(即变换后直线还是直线圆弧还是圆弧)和“平行性”(其实是保持二维图形间的相对位置关系不变平行线还是平行线而直线上的点位置顺序不变另特别注意向量间夹角可能会发生变化)。仿射变换可以通过一系列的原子变换的复合来实现包括平移(Translation)、缩放(Scale)、翻转(Flip)、旋转(Rotation)和错切(Shear)。
仿射变化也是需要一个M矩阵就可以但是由于仿射变换比较复杂很难找到这个矩阵opencv提供了根据变换前后三个点的对应关系来自动求解M 这个函数是cv2.getAffineTransoform(pts1, pts2)
事实上仿射变换代表的是两幅图之间的关系我们通常使用2x3矩阵来表示仿射变换如下:img cv2.imread(4.jpg)
rows, cols img.shape[:2]
pts1 np.float32([[50, 50], [200, 50], [50, 200]])
pts2 np.float32([[10, 100], [200, 50], [100, 250]])
# 类似于构造矩阵
M cv2.getAffineTransform(pts1, pts2)
res cv2.warpAffine(img, M, (cols, rows))
cv2.imshow(原图, img)
cv2.imshow(res, res)
cv2.waitKey(0)
cv2.destroyAllWindows()五图像的透射
仿射变换(affine transform)与透视变换(perspective transform)在图像还原、图像局部变化处理方面有重要意义。通常在2D平面中仿射变换的应用较多而在3D平面中透视变换又有了自己的一席之地。两种变换原理相似结果也类似可针对不同的场合使用适当的变换。
基于3×3矩阵进行的变换叫透视变换或者单应性映射。
仿射变换可以形象的表示成以下形式。一个平面内的任意平行四边形ABCD可以被仿射变换映射为另一个平行四边形A’B’C’D’。通俗的解释就是可以将仿射变换想象成一幅图像画到一个胶版上在胶版的角上推或拉使其变形而得到不同类型的平行四边形。相比较仿射变换透射变换更具有灵活性一个透射变换可以将矩形转变成梯形。
img cv2.imread(4.jpg)
rows, cols img.shape[:2]
pts1 np.float32([[56, 65], [238, 52], [28, 237], [239, 240]])
pts2 np.float32([[0, 0], [200, 0], [0, 200], [200, 200]])
M cv2.getPerspectiveTransform(pts1, pts2)
res cv2.warpPerspective(img, M, (cols, rows))
cv2.imshow(yuantu, img)
cv2.imshow(res, res)
cv2.waitKey(0)
cv2.destroyAllWindows()