两件事:
您将补丁矩阵初始化为错误的数据类型。默认情况下,numpy 将使补丁矩阵成为np.float64 类型,如果您将其与保存一起使用,您将无法获得预期的结果。具体来说,如果您咨询Mr. F's answer,实际上在浮点图像上执行了一些缩放,其中图像的最小值和最大值分别缩放为黑色和白色,因此如果您的图像在背景中完全一致,最小值和最大值都将相同,并将显示为黑色。因此,最好的办法是尊重原始图像的数据类型,即将补丁矩阵的dtype 设置为np.uint8。
从您的 for 循环索引判断,您想要提取出 8 x 8 的 非重叠补丁。这意味着,如果您有一个 32 x 32 的图像和 8 x 8 块,那么您总共有 16 个块排列在 4 x 4 网格中。
因此,您需要更改 patches 语句,使其在第一维中具有 16,而不是 36。此外,您必须调整索引到图像的方式以提取 8 x 8 个补丁,因为现在补丁是重叠的。具体来说,您想让图像补丁索引从8*i 到8*(i+1) 的行和8*j 到8*(j+1) 的列。如果您自己替换 i 和 j 的样本值,您会看到我们为您的图像中的每个网格获得了唯一的 8 x 8 补丁。
以上两点我都注意到了,修改后的代码应该是:
import scipy.ndimage as ndimage
import scipy.misc as misc
import numpy as np
image32 = misc.imread('work0.png')
patches = np.zeros((16,8,8), dtype=np.uint8) # Change
for i in range(4):
for j in range(4):
patches[i*4 + j] = image32[8*i:8*(i+1),8*j:8*(j+1)] # Change
misc.imsave("{0}{1}.png".format(i,j), patches[i*4 + j])
当我这样做并查看输出图像时,我得到了我所期望的。
绝对确定,让我们使用matplotlib 绘制段。您已经方便地将所有补丁保存在 patches 中,因此显示我们需要的内容应该不是问题。但是,我将在 cmets 中放置一些代码,以便您可以读取使用上述代码从磁盘保存的图像,这样您就可以验证它是否仍然有效,无论查看 patches 或磁盘上的图像:
import matplotlib.pyplot as plt
plt.figure()
for i in range(4):
for j in range(4):
plt.subplot(4, 4, 4*i + j + 1)
img = patches[4*i + j]
# or you can do this:
# img = misc.imread('{0}{1}.png'.format(i,j))
img = np.dstack([img, img, img])
plt.imshow(img)
plt.show()
matplotlib.pyplot.imshow 的奇怪之处在于,如果您的图像是单通道图像(例如您的情况),并且周围具有相同的强度,那么无论颜色图是什么,它都会被可视化为黑色,就像我们对imsave 的体验。因此,我必须人为地将其制作为 RGB 图像,但所有通道都相同,以便在显示图像之前将其可视化为灰度。
我们得到: