最近刚刚看了“Spatial Transformer Network“这篇论文和李宏毅老师的相关视频,正好简单整理一下F.grid_sample和F.affine_grid这一对函数操作。
F.affine_grid函数是根据仿射变换矩阵,生成该变换相对应的逐像素偏移矩阵;
F.grid_sample函数则是根据这个偏移矩阵将原始图片逐像素扭曲warp到目标位置处形成一个新的图片。
这里引入一个小的知识点:
Spatial Transformer Network
具体可以参考“Spatial Transformer Network“这篇论文,以及李宏毅老师的视频讲解更加容易理解。(李宏毅老师yyds)
论文下载:https://proceedings.neurips.cc//paper/2015/file/33ceb07bf4eeb3da587e268d663aba1a-Paper.pdf
李宏毅老师主页:https://speech.ee.ntu.edu.tw/~hylee/
①Locaisation net
输入图片经过Locaisation net网络生成一个仿射变换参数
②Grid generator(坐标)
根据这个仿射变换参数得到输入图片与输出图片间的坐标映射关系
③Sampler(像素值)
通过目标坐标,从输入图片中采样对应的像素值填充到目标坐标系中,为了防止梯度消失,一般采用双线性插值法
言归正传:
下面利用python写一段小程序将图片逆时针旋转45°
from PIL import Image
import torch
import torch.nn.functional as F
from torchvision.transforms import ToTensor, ToPILImage
def pil_loader(path):
with open(path, 'rb') as f:
with Image.open(f) as img:
return img.convert('RGB')
img = pil_loader('1.jpg')
img.show()
img = ToTensor()(img).unsqueeze(0) # img→tensor 3维→4维
M = torch.tensor( # 仿射变换矩阵
[[[0.7071, -0.7071, 0],
[0.7071, 0.7071, 0]]]
)
grid = F.affine_grid(M, size=(1, 3, 500, 500))
warp_img = F.grid_sample(img, grid) # 扭转图片
tensor_to_pil = ToPILImage() # tensor→img
tensor_to_pil(warp_img.data.squeeze(0)).show() # 4维→3维
输出结果:
这里一定要注意维度的对应!!!!!!!!
中间有关于show()不能显示图片的问题。
Python中的PIL的img.show()函数不能显示图像
运行结果没有报错,但是不能显示图片,原因是由于没有设置默认打开图片的软件。
解决办法:搜索画图软件(或者浏览器),将其设置为默认打开jpg或bmp等类型图片的软件,即可。
待更新…