所有的图像预处理操作都是基于解码之后的tensor进行操作的
图像数据处理
通过图像的预处理,可以尽量避免模型受到无关因素的影响;在大部分的图像预处理过程可以提高模型的准确率
图像编码处理
因为图像在存储过程中并不是直接记录这些矩阵中的数字,而是记录经过压缩编码之后的结果;所有将一张图像还原成一个三维矩阵需要解码的过程;tensorflow提供了对jpeg和png格式图像的编码/解码函数;
import tensorflow as tf
import matplotlib.pyplot as plt
# 读取图像的原始数据
image_raw_data = tf.gfile.FastGFile('D:/2019-02/image18.jpg', 'rb').read()
with tf.Session() as sess:
# 对图像进行jpeg的格式解码从而得到图像对应的三维矩阵;tensorflow还提供了tf.image.decode_png
# 函数对png格式的图像进行解码,解码之后结果为一个张量,在使用它的取值之前需要明确调用运行的过程
image_data = tf.image.decode_jpeg(image_raw_data)
print(image_data.eval())
# 使用pyplot工具可视化得到的图像
plt.imshow(image_data.eval())
plt.show()
# 将表示一张图像的三维矩阵重新按照jpeg格式编码并存入文件中去,可以得到和原图一样的图像
encoded_image = tf.image.encode_jpeg(image_data)
# with tf.gfile.GFile('/path/to/output', 'wb') as f:
# f.writer(encoded_image.eval())
原图像:
图像大小调整
一般来说,网络上获取的图像大小是不固定的,但神经网络输入节点的个数是固定的;所以在将图像的像素作为输入提供给神经网络之前,需要将图像的大小统一,这就是图像大小调整需要完成的任务;图像的调整方法有两种方式,一种是通过算法使得新的图像尽量保存到原始图像上的所有信息
import tensorflow as tf
import matplotlib.pyplot as plt
# 读取图像的原始数据
image_raw_data = tf.gfile.FastGFile('D:/2019-02/image18.jpg', 'rb').read()
with tf.Session() as sess:
# 对图像进行jpeg的格式解码从而得到图像对应的三维矩阵;tensorflow还提供了tf.image.decode_png
# 函数对png格式的图像进行解码,解码之后结果为一个张量,在使用它的取值之前需要明确调用运行的过程
image_data = tf.image.decode_jpeg(image_raw_data)
# print(image_data.eval())
# 将0-255的像素值转化为0-1之间
# 大多数API都支持整数和实数的输入,如果输入是整型类型,这些API会在内部输入转化为实数后处理,在将输出转换为整数;
# 如果有多个处理数据,在整数和实数之间的反复转换会导致精度损失,因此推荐在图像处理前将其转换为实数类型
image_data = tf.image.convert_image_dtype(image_data, dtype=tf.float32)
print(image_data.eval())
# 通过tf.image.resize_images函数调整图像的大小
# 第三个参数表示图像调整大小的算法
resized = tf.image.resize_images(image_data, [300,300], method=0)
plt.imshow(resized.eval())
plt.show()
输出结果:
[[[1. 1. 1. ] [1. 1. 1. ] [0.9960785 1. 1. ] ... [1. 1. 1. ] [1. 1. 1. ] [1. 1. 1. ]] [[1. 1. 1. ] [1. 1. 1. ] [0.9960785 1. 1. ] ... [1. 1. 1. ] [1. 1. 1. ] [1. 1. 1. ]] [[1. 1. 1. ] [1. 1. 1. ] [0.9960785 1. 1. ] ... [1. 1. 1. ] [1. 1. 1. ] [1. 1. 1. ]] ... [[1. 0.9921569 1. ] [1. 0.9921569 1. ] [1. 0.9921569 1. ] ... [1. 1. 1. ] [1. 1. 1. ] [1. 1. 1. ]] [[1. 0.9921569 1. ] [1. 0.9921569 1. ] [1. 0.9921569 1. ] ... [1. 1. 1. ] [1. 1. 1. ] [1. 1. 1. ]] [[1. 0.9921569 1. ] [1. 0.9921569 1. ] [1. 0.9921569 1. ] ... [1. 1. 1. ] [1. 1. 1. ] [1. 1. 1. ]]]
method值 | 图像调整算法大小 |
0 | 双线性插值法 |
1 | 最近邻居法 |
2 | 双三次插值法 |
3 | 面积插值法 |
第二种方法就是对图像进行裁剪或者填充
import tensorflow as tf
import matplotlib.pyplot as plt
# 读取图像的原始数据
image_raw_data = tf.gfile.FastGFile('D:/2019-02/image18.jpg', 'rb').read()
with tf.Session() as sess:
image_data = tf.image.decode_jpeg(image_raw_data)
print(image_data.eval().shape)
croped = tf.image.resize_image_with_crop_or_pad(image_data, 300, 300)
padded = tf.image.resize_image_with_crop_or_pad(image_data, 1000, 1000)
# plt.imshow(croped.eval())
plt.imshow(padded.eval())
plt.show()
原图像:
裁剪后的:
扩充后的:
图像翻转
tensorflow提供了一些函数来支持对图像的翻转
import tensorflow as tf
import matplotlib.pyplot as plt
# 读取图像的原始数据
image_raw_data = tf.gfile.FastGFile('D:/2019-02/image18.jpg', 'rb').read()
with tf.Session() as sess:
image_data = tf.image.decode_jpeg(image_raw_data)
# 左右翻转
# flipped = tf.image.flip_left_right(image_data)
# 上下翻转
flipped = tf.image.flip_up_down(image_data)
# 沿对角线翻转
transposed = tf.image.transpose_image(image_data)
# 以50%的概率上下翻转图像
flipped = tf.image.random_flip_left_right(image_data)
# 以50%的概率左右翻转图像
flipped = tf.image.random_flip_up_down(image_data)
plt.imshow(transposed.eval())
plt.show()
上下翻转:
左右翻转
对角线翻转