You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用PIL fromarray导入RGB数组生成PNG显示异常,求原因及正确方法

问题描述

想用PIL的fromarray方法把RGB数组导入并保存为带元数据的PNG,代码如下:

import numpy as np
from PIL import Image
from PIL.PngImagePlugin import PngInfo
a = np.array([[[255, 0, 0], [0, 255, 0]],     # 红   绿
              [[0, 0, 255], [0, 0, 0]]])      # 蓝   黑  
img = Image.fromarray(a, mode="RGB")   
metadata = PngInfo()                    # 需要添加元数据,所以用Pillow而不是cv2
metadata.add_text("key", "value")
img.save("test.png", pnginfo=metadata)

但输出图像显示为红 黑 黑 黑,而非预期的红 绿 蓝 黑。尝试RGBA数组也出现类似问题:

a = np.array([[[255, 0, 0, 255], [0, 255, 0, 255]],     # 红   绿
              [[0, 0, 255, 255], [0, 0, 0, 255]]])      # 蓝   黑  
原因分析

numpy创建数组时默认的dtype是int64,而PIL的fromarray在处理RGB/RGBA模式时,要求输入数组必须是uint8类型(0-255的无符号整数)。当传入int64类型的数组时,PIL无法正确解析数值(即便表面数值在0-255范围内,但类型不匹配),导致除第一个像素外的其他像素被识别为无效值,最终显示为黑色。

解决方法

创建numpy数组时显式指定dtype=np.uint8,或者将已有数组转换为uint8类型即可。

修正后的RGB代码

import numpy as np
from PIL import Image
from PIL.PngImagePlugin import PngInfo
# 显式指定dtype为uint8
a = np.array([[[255, 0, 0], [0, 255, 0]],
              [[0, 0, 255], [0, 0, 0]]], dtype=np.uint8)
img = Image.fromarray(a, mode="RGB")   
metadata = PngInfo()
metadata.add_text("key", "value")
img.save("test.png", pnginfo=metadata)

修正后的RGBA代码

import numpy as np
from PIL import Image
from PIL.PngImagePlugin import PngInfo
a = np.array([[[255, 0, 0, 255], [0, 255, 0, 255]],
              [[0, 0, 255, 255], [0, 0, 0, 255]]], dtype=np.uint8)
img = Image.fromarray(a, mode="RGBA")   
metadata = PngInfo()
metadata.add_text("key", "value")
img.save("test_rgba.png", pnginfo=metadata)

如果数组已经创建完成,也可以通过a = a.astype(np.uint8)转换类型后再传入fromarray。


内容的提问来源于stack exchange,提问作者Basj

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.09 20:08:12