您当前的位置:首页 > IT编程 > 图像修复
| C语言 | Java | VB | VC | python | Android | TensorFlow | C++ | oracle | 学术与代码 | cnn卷积神经网络 | gnn | 图像修复 | Keras | 数据集 | Neo4j | 自然语言处理 | 深度学习 | 医学CAD | 医学影像 | 超参数 | pointnet | pytorch |

自学教程:Possible precision loss when converting from float64 to uint16 .format(dtypeobj_in, dtypeobj_out))

51自学网 2020-06-07 18:17:16
  图像修复
这篇教程Possible precision loss when converting from float64 to uint16 .format(dtypeobj_in, dtypeobj_out))写得很实用,希望能帮到您。
《Tensorflow:实战Google深度学习框架(第2版)》中有一句话:
大多数图像处理API支持整数和实数类型的输入。如果输入是整数类型,这些API会在内部将输入转化为实数后处理,再将输出转化为整数。如果有多个处理步骤,在整数和实数之间的反复转化将导致精度损失,因此推荐在图像处理前将其转化为实数类型。

编程中常见的一种警告:

/Library/Python/2.7/site-packages/skimage/util/dtype.py:141: UserWarning: Possible precision loss when converting from float64 to uint8
  .format(dtypeobj_in, dtypeobj_out))
/Library/Python/2.7/site-packages/skimage/util/dtype.py:141: UserWarning: Possible precision loss when converting from float64 to uint16
  .format(dtypeobj_in, dtypeobj_out))

    1
    2
    3
    4

Possible precision loss when converting from float to uint的意思是这意味着可能发生的精度损失。

总之,我们在使用图像处理API前,最好将图像数据转化为float型。

既然这样,我们就必须知道整型和实型图像数组的区别:

整型RGB图像数组元素值范围是0~255,实型RGB图像数组元素值范围是0~1;

Lab图像数组元素范围是:L的范围是0~100(代表亮度),a和b的范围均为-128~127(代表颜色),不管Lab图像数组是整型还是实型,范围都是这个。

另外再补充一点,skimage的颜色空间转换函数(比如rgb2lab(),lab2rgb())的参数可以是整型或者实型,返回值都是实型。

注意到以上所讲的整型和实型的RGB图像数组范围不一致,这是我们需要注意的地方。下面进行整型和实型的RGB图像数组的使用对比:

现在我手头上有int型RGB图像数组rgb_image,要将图像转化为Lab格式只需下面一句:、

    1

返回的lab_image数组是float型的。

和上述情况形成对比的是:为了照顾精度,要先将rgb_image转化为float型,再使用rgb2lab()。将整型RGB图像数组转化为实型后,由于要符合实型RGB图像数组的数据范围,所以要除以255.0f:

……    # "……"代表将rgb_image数组元素转化为float型的操作,由于仅做了数据类型转化,
    # 所以数据范围依旧是0~255
    
rgb_image = rgb_image / 255.0f        # 作用就是使图像数组数据范围符合实型RGB图像数组的要求。
                                    # 如果不加这一句,则得到的lab_image图像数组范围超出正常,
                                    # 且程序不会报错
lab_image = rgb2lab(rgb_image)

    1
    2
    3
    4
    5
    6
    7

上述操作返回的lab_image也是float型数组,注意上述代码的/255.0f尤为重要,不然得到的lab_image数组元素数值范围会特别大。

既然整型和实型的RGB数组使用有区别,那么整型和实型的Lab图像数组有没有区别呢?

当然没有:
若我手头上有Lab图像数组,由于整型和实型的Lab图像数组范围一致,所以使用lab2rgb()时不需要改变数组元素值的范围:

rgb_image = lab2rgb(lab_image)    # 无论lab_image是整型还是实型,这一句都足够了

    1

利用Tensorflow+skimage实现颜色空间转换

根据之前所讲,当我们给rgb2lab()传入一个实型数组时,需要检查这个数组的范围是否在0~1之间,如果你将整型RGB数组转化为实型RGB数组的操作仅仅是改变了数组元素的类型,而没有改变数值范围,则程序不会报错,但得到的Lab图像数组范围会很大。

tensorflow有个函数可以将整型RGB图像转化为实型RGB图像,转化的过程不仅改变数组元素的类型,还会自动将数值范围限制在0~1.

下面给出博主实践用的代码(注意每个代码片的缩进是同步的),结合代码理解:

import tensorflow as tf
from skimage.color import rgb2lab, lab2rgb

image_raw_data = tf.gfile.FastGFile("rgb_picture/2.jpg", 'r').read() # 读取一个RGB图像
with tf.Session() as sess:
    img_data = tf.image.decode_jpeg(image_raw_data)    # 此时img_data是整型图像数组的tensor
    print img_data.eval()

    1
    2
    3
    4
    5
    6
    7

输出的是整型RGB图像数矩阵,范围在0~255:


[[[  1  94 215]
  [  0  93 214]
  [  0  93 214]
  ...
  [  0 105 223]
  [  0 105 223]
  [  0 105 223]]

 [[  1  94 215]
  [  0  93 214]
  [  0  93 214]
  ...

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12

利用tensorflow的函数将图像转换为float型图像

    img_data = tf.image.convert_image_dtype(img_data, dtype=tf.float32)
    print img_data.eval()   # 输出的图片数据矩阵,数据范围都在0~1间。
                # 加eval()是因为img_data是tensor,获取其值需要用eval()或者sess.run(),下同。

    1
    2
    3

输出float型RGB图像数据矩阵,且数值范围自动限制在0~1间:

[[[0.00392157 0.36862746 0.8431373 ]
  [0.         0.3647059  0.83921576]
  [0.         0.3647059  0.83921576]
  ...
  [0.         0.41176474 0.8745099 ]
  [0.         0.41176474 0.8745099 ]
  [0.         0.41176474 0.8745099 ]]
 ...

    1
    2
    3
    4
    5
    6
    7
    8
    9

然后将图像转化为Lab格式():

    img_data = rgb2lab(img_data.eval())
    print img_data      # 返回的lab图片数据矩阵是float型,但数据范围不在-1~1间

    1
    2

输出Lab图像数组如下,可以看到这个Lab图像数组虽为实型,但不像实型的RGB图像数组,它的数值范围和整型Lab图像数组是一致的:


[[[ 42.63580875  24.91225502 -68.08540347]
  [ 42.27894392  25.14236119 -68.09560274]
  [ 42.27894392  25.14236119 -68.09560274]
  ...
  [ 46.21493852  20.89131147 -66.81553317]
  [ 46.21493852  20.89131147 -66.81553317]
  [ 46.21493852  20.89131147 -66.81553317]]
  ...

    1
    2
    3
    4
    5
    6
    7
    8

然后将这个Lab作为别的图像颜色空间转换函数的参数,不需要修改它的数值范围,不像不符合要求的RGB图像矩阵要手动除以255以确保符合实型图像数据-1~1的范围要求。

    img_data = lab2rgb(img_data)    # 如果你多此一举地将作为Lab图像数组的img_data
                                    # 的数值范围限制在-1~1间,程序会报错
    print img_data      # 返回的rgb图片数据矩阵是float型,数据范围在-1~1间

    1
    2
    3

瞧瞧这返回的RGB图像矩阵,毫无疑问,范围又被限制回-1~1间:

[[[3.92156872e-03 3.68627461e-01 8.43137327e-01]
  [0.00000000e+00 3.64705893e-01 8.39215782e-01]
  [0.00000000e+00 3.64705893e-01 8.39215782e-01]
  ...
  [0.00000000e+00 4.11764747e-01 8.74509950e-01]
  [0.00000000e+00 4.11764747e-01 8.74509950e-01]
  [0.00000000e+00 4.11764747e-01 8.74509950e-01]]
  ...

    1
    2
    3
    4
    5
    6
    7
    8

小结:

(1)颜色空间转换函数的返回值均为float型,如果返回的是RGB图像矩阵,则其范围符合-1~1的范围要求
(2)颜色空间转换函数的参数可以是整型图像矩阵也可以是实型,如果参数是RGB图像数组,则传入实型数组时,要确保将数据范围限制在-1~1之间(方式是除以255),更确切讲其实是0~1间,因为RGB值不可能为负;如果传入的是Lab图像数组,不管数组元素是整型还是实型,都无需关心其范围,反倒是将数据限制在-1~1间会出错。
————————————————
版权声明:本文为CSDN博主「umbrellalalalala」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/umbrellalalalala/java/article/details/86765792
自动给黑白照片上色
keras学习笔记-黑白照片自动着色的神经网络-Beta版
51自学网,即我要自学网,自学EXCEL、自学PS、自学CAD、自学C语言、自学css3实例,是一个通过网络自主学习工作技能的自学平台,网友喜欢的软件自学网站。
京ICP备13026421号-1