如何将 EXR 文件的 Python 中的 float16 转换为 uint8
How to convert float16 to uint8 in Python for EXR files
我正在使用 OpenEXR 读取 Python 中的 EXR 文件。我有带半数据 (float16) 的 R、G 和 B 通道。我尝试使用 Numpy 将数据从 float16 转换为 uint8(0-255 色),但没有成功。
rCh = getChanEXR(imageFile, 'R','HALF')
rCh = np.array(rCh).astype('uint8')
所以,我把R通道的像素值赋给了一个变量rCh。然后我将 array.array 转换为 np.array,以便我可以使用 astype 方法将其转换为 uint8。我是新手,所以我显然不正确,因为所有值都变为 0。最初,值是这样的:0.0、2.9567511226945634e-14、1.2295237050707897e-10 等
除了 float16 值之外,我还有一些需要规范化的常规 float 值。我想我需要先规范化 float16 值,然后才能将它们设置在 0-255 的范围内。
有什么想法吗?谢谢。
添加此处 getChanEXR 中提到的 def 的代码(只是基于 python OpenEXR 文档中用于获取通道数据的代码的自定义 def。
def getChanEXR(curEXRStr, curChannel, dataType):
#import OpenEXR, Imath, array
pt = 'none'
if dataType == 'HALF':
pt = Imath.PixelType(Imath.PixelType.HALF)
if dataType == 'FLOAT':
pt = Imath.PixelType(Imath.PixelType.FLOAT)
if dataType == 'UINT':
pt = Imath.PixelType(Imath.PixelType.UINT)
chanstr = OpenEXR.InputFile(curEXRStr).channel(curChannel, pt)
chan = array.array('f', chanstr)
return chan
我对 array.array
没有太多经验,但我相信您可以将其转换为 numpy 浮点数组,这样使用起来会更容易一些:
rCh = np.asarray(rCh, dtype=np.float)
如果您的数据在 [0,1]
中标准化,则在转换之前将其乘以 255:
rCh = np.asarray(rCh * 255, dtype=np.uint8)
我相信它会截断小数部分。手动舍入应该更安全吧? (不太确定,请参阅评论中的讨论,我相信正确的方法会在这里犹豫不决,但我想这个问题值得针对您的具体用例进行更好的研究)
rCh = np.asarray(np.around(rCh * 255), dtype=np.uint8)
如果它没有标准化,你可以做
rCh -= rCh.min()
rCh /= rCh.max()
然后转换成8bits
rCh = np.asarray(rCh * 255, dtype=np.uint8)
我正在使用 OpenEXR 读取 Python 中的 EXR 文件。我有带半数据 (float16) 的 R、G 和 B 通道。我尝试使用 Numpy 将数据从 float16 转换为 uint8(0-255 色),但没有成功。
rCh = getChanEXR(imageFile, 'R','HALF')
rCh = np.array(rCh).astype('uint8')
所以,我把R通道的像素值赋给了一个变量rCh。然后我将 array.array 转换为 np.array,以便我可以使用 astype 方法将其转换为 uint8。我是新手,所以我显然不正确,因为所有值都变为 0。最初,值是这样的:0.0、2.9567511226945634e-14、1.2295237050707897e-10 等
除了 float16 值之外,我还有一些需要规范化的常规 float 值。我想我需要先规范化 float16 值,然后才能将它们设置在 0-255 的范围内。
有什么想法吗?谢谢。
添加此处 getChanEXR 中提到的 def 的代码(只是基于 python OpenEXR 文档中用于获取通道数据的代码的自定义 def。
def getChanEXR(curEXRStr, curChannel, dataType):
#import OpenEXR, Imath, array
pt = 'none'
if dataType == 'HALF':
pt = Imath.PixelType(Imath.PixelType.HALF)
if dataType == 'FLOAT':
pt = Imath.PixelType(Imath.PixelType.FLOAT)
if dataType == 'UINT':
pt = Imath.PixelType(Imath.PixelType.UINT)
chanstr = OpenEXR.InputFile(curEXRStr).channel(curChannel, pt)
chan = array.array('f', chanstr)
return chan
我对 array.array
没有太多经验,但我相信您可以将其转换为 numpy 浮点数组,这样使用起来会更容易一些:
rCh = np.asarray(rCh, dtype=np.float)
如果您的数据在 [0,1]
中标准化,则在转换之前将其乘以 255:
rCh = np.asarray(rCh * 255, dtype=np.uint8)
我相信它会截断小数部分。手动舍入应该更安全吧? (不太确定,请参阅评论中的讨论,我相信正确的方法会在这里犹豫不决,但我想这个问题值得针对您的具体用例进行更好的研究)
rCh = np.asarray(np.around(rCh * 255), dtype=np.uint8)
如果它没有标准化,你可以做
rCh -= rCh.min()
rCh /= rCh.max()
然后转换成8bits
rCh = np.asarray(rCh * 255, dtype=np.uint8)