Matlab彩色图像旋转的数学原理及实现

一、引言

图像的几何变换在图像处理中被经常使用,其中图像旋转又是使用频率很高的变换,不仅应用于普通的图像的处理中,也会用于机器学习中的图像数据增强。图像旋转的数学原理很简单,就是简单的矩阵乘法。
图像旋转示意图如下图所示,其中左图是旋转之前图像,右图是旋转之后的图像。
在这里插入图片描述
本文给出了图像旋转的详细实现过程。此外也给出了matlab软件自带的图像旋转函数imrotate的用法。

二、数学原理及公式

学过线性代数的童鞋都知道如下的矩阵表示旋转矩阵:
在这里插入图片描述
且当矩阵左乘向量时,表示逆时针旋转,否则表示顺时针旋转。
该旋转矩阵的由来其实也非常简单,就是用到了简单的三角公式而已。如下图所示:
在这里插入图片描述
假设旋转之前的坐标为(x,y),绕坐标原点旋转之后的坐标为(x*, y*),为讨论方便可以把这两组坐标点放到单位圆上。则可以得到两组坐标和角度之间的关系如下:
在这里插入图片描述
在这里插入图片描述
把右端项展开即可得:
在这里插入图片描述
写出矩阵形式为:
在这里插入图片描述
因此,对于图像旋转而言,其实就是像素的坐标旋转,像素跟着坐标走而已。

三、matlab实现图像旋转

1.旋转映射
由于图像像素旋转一定角度后,其坐标可能不再是整数坐标,而且可能会产生多个像素旋转之后对应到同一个像素而导致旋转之后的图像丢失像素。为了解决此问题,采用逆向思维,即构造一个映射,把旋转之后的像素坐标映射到原图像的像素坐标,这样就可以保证旋转之后的每个像素均有像素值。
在这里插入图片描述
此时旋转就变成了顺时针,因此旋转矩阵为:
在这里插入图片描述
由于引入了映射,即旋转变换,因此会产生非整数点的坐标,所以需要引入图像插值方法。由于本文的主要工作是图像旋转,因此仅仅采用最近邻插值方法。
2.单通道图像中心化旋转
图像旋转是以图像中心为旋转轴,因此图像在旋转之前需要把像素坐标进行中心化,然后再旋转,代码如下:
假设图像矩阵image和旋转角度angle已知,且image是单通道数据。

[ h, w ] = size( image );
im = uint8( zeros( h, w ) );%创建空的旋转图像矩阵,此处uint8是必须的
RotMatrix = [ cos(angle), -sin(angle); sin(angle), cos(angle) ];%旋转矩阵
halfH = floor( h / 2 );
halfW = floor( w / 2 );
%逐个像素计算其旋转前的位置及像素
for i = 1 : h
    for j = 1 : w
        coord = [ i-halfH, j-halfW ] * RotMatrix;%中心化旋转
        ir = round( coord( 1 ) ) + halfH;%恢复到原图像的行坐标分量
        jr = round( coord( 2 ) ) + halfW;%恢复到原图像的列坐标分量
        if ir > 0 & ir <= h & jr > 0  & jr <= w
            im( i, j ) = image( ir, jr ); %按照最近邻插值法获取图像数据
        end
    end
end

3.三通道图像中心化旋转
可以把单通道图像中心化旋转做成一个函数,然后针对R、G、B分量分别调用单通道旋转即可。
假设单通道图像旋转函数为:

function im = ImRotation( image, angle )

则三通道图像旋转可以如下实现:

imSize = size( image );
R = image( :, :, 1 );
G = image( :, :, 2 );
B = image( :, :, 3 );
imR = ImRotation( R, angle );
imG = ImRotation( G, angle );
imB = ImRotation( B, angle );
im = uint8( zeros( imSize ) );
im( :, :, 1 ) = imR;
im( :, :, 2 ) = imG;
im( :, :, 3 ) = imB;

4.完整的图像中心化旋转代码

function im = ImageRotation( image, angle )
%图像逆时针中心化旋转
imSize = size( image );
dim = numel( imSize ); %图像的维数
if( dim == 2 )%单通道图像,即灰度图像
    im = ImRotation( image, angle );
else%彩色图像,即三通道图像
    R = image( :, :, 1 );
    G = image( :, :, 2 );
    B = image( :, :, 3 );
    imR = ImRotation( R, angle );
    imG = ImRotation( G, angle );
    imB = ImRotation( B, angle );
    im = uint8( zeros( imSize ) );
    im( :, :, 1 ) = imR;
    im( :, :, 2 ) = imG;
    im( :, :, 3 ) = imB;
    %im = cat(3 ,imR, imG, imB );%将三个颜色分量合成彩色图像
end
end
 
%针对单通道颜色分量绕图像中心逆时针旋转
function im = ImRotation( image, angle )
[ h, w ] = size( image );
im = uint8( zeros( h, w ) );%创建空的旋转图像矩阵,此处uint8是必须的
RotMatrix = [ cos(angle), -sin(angle); sin(angle), cos(angle) ];%旋转矩阵
halfH = floor( h / 2 );
halfW = floor( w / 2 );
%逐个像素计算其旋转前的位置及像素
for i = 1 : h
    for j = 1 : w
        coord = [ i-halfH, j-halfW ] * RotMatrix;%中心化旋转
        ir = round( coord( 1 ) ) + halfH;%恢复到原图像的行坐标分量
        jr = round( coord( 2 ) ) + halfW;%恢复到原图像的列坐标分量
        if ir > 0 & ir <= h & jr > 0  & jr <= w
            im( i, j ) = image( ir, jr ); %按照最近邻插值法获取图像数据
        end
    end
end
end

5.测试上述旋转函数

clear all
clc
image = imread( '1.jpg' );
figure(1); imshow( image );
angle = pi/4;
im = ImageRotation( image, angle );
figure;imshow( im );
angle = -pi/4;
im = ImageRotation( image, angle );
figure;imshow( im );

运行结果:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

四、matlab命令imrotate

语法规则:
output = imrotate( matrix, angle, method )
其中matrix是图像矩阵,可以是单通道,也可以是多通道
angle是旋转角度,单位是度°,正值为逆时针,负值为顺时针
method是插值方法,可以是nearest、bilinear等
output是旋转之后的图像。该图像将根据原图像的大小和旋转角度计算旋转之后的图像大小,以保证原图像都在视图之内。
例如:

I = imread('rice.png');
J = imrotate(I,45,'nearest');
imshow(J)

运行结果如下:
在这里插入图片描述

  • 11
    点赞
  • 42
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值