用 OpenCV Python 编写超过 4 个通道的图像

tpu*_*GIS 8 python opencv numpy image

这对我来说是一个持续的挑战。我正在尝试使用 openCV 将两个 3 RGB 图像组合成单个 6 通道 TIFF 图像。

到目前为止,我的代码如下:

import cv2
import numpy as np

im1 = cv2.imread('im1.jpg')
im2 = cv2.imread('im2.jpg')

merged = np.concatenate((im1, im2), axis=2) # creates a numpy array with 6 channels 

cv2.imwrite('merged.tiff', merged)
Run Code Online (Sandbox Code Playgroud)

我也尝试过使用 openCV 的 split() 和 merge() 方法并获得相同的结果

import cv2
import numpy as np

im1 = cv2.imread('im1.jpg')
im2 = cv2.imread('im2.jpg')

b1,g1,r1 = cv2.split(im1)
b2,g2,r2 = cv2.split(im2)

merged = cv2.merge((b1,g1,r1,b2,g2,r2))

cv2.imwrite('merged.tiff', merged)
Run Code Online (Sandbox Code Playgroud)

当我运行 imwrite() 函数时,出现以下错误:

OpenCV 错误:断言失败 (image.channels() == 1 || image.channels() == 3 || image.channels() == 4) in cv::imwrite_, 文件 C:\builds\master_PackSlaveAddon-win32 -vc12-static\opencv\modules\imgcodecs\src\loadsave.cpp,第 455 行
回溯(最近一次调用最后一次):
  文件“”,第 1 行,在 
cv2.error: C:\builds\master_PackSlaveAddon-win32-vc12-static\opencv\modules\imgcodecs\src\loadsave.cpp:455: 错误: (-215) image.channels() == 1 || image.channels() == 3 || 函数 cv::imwrite_ 中的 image.channels() == 4

两个图像的尺寸相同 (900X1200)。我认为 openCV 不能将超过 4 个通道 (RGBA) 写入 tiff 图像,而且我没有找到另一种编码此图像的方法。

我正在考虑创建自己的函数来编写带有适当标题的二进制数据,但这比我想要的要深入得多。

openCV 中是否有另一个我可以使用的函数,或者另一个可以将此 numpy 数组写入 6 个通道的 tiff 的库?

Zda*_*daR 6

OpenCV的用途libpnglibtiff等模块内部写RGB图像,作为各种图像表示格式喜欢jpgpng等假设的事实,即输入阵列必须是一个单个信道,信道3或4频道。假设是为了优化图像的磁盘大小。但是在 6 通道矩阵中会违反相同的假设。

因此,您可以使用类似的序列化库pickle,它通常可用于序列化任何 Python 对象,在这种情况下,您希望序列化一个 numpy 矩阵,因此它可以正常工作,但是您将无法利用pngjpg格式使用的压缩技术。

import numpy as np
import pickle

arr = np.ones((1000, 1000, 6), dtype=np.uint8) * 255

with open("arr_dump.pickle", "wb") as f_out:
    pickle.dump(arr, f_out)

with open("arr_dump.pickle", "rb") as f_in:
    arr_new = pickle.load(f_in)
    print arr_new.shape
Run Code Online (Sandbox Code Playgroud)

但是,如果您关心文件的大小,并希望使用tifforpng等的内存优化,那么我建议您将 6 通道图像拆分为各个通道并创建 2 个新的 3 通道矩阵并使用 imwrite对它们进行保存,并在阅读时读取两个图像并将它们组合成 6 通道图像。