gzip压缩解压图片失败?

文章讲述了使用OpenCV进行图片处理,通过小波变换压缩RGB通道的图片,然后利用CSR稀疏矩阵存储并用gzip压缩数据。在传输后,通过解压和恢复CSR矩阵,但遇到了数据类型匹配问题导致矩阵为空。最终发现解压时需明确数据类型(如int32)以正确恢复矩阵。
摘要由CSDN通过智能技术生成

又是被坑的一天~

我想压缩一张图片origin.png,百度图片将就找一张吧。1101103的彩图:
在这里插入图片描述

先读进来:

img = cv2.imread('D:/Secondcoding/remote/origin.png')

然后我对它分成了三通道对每一个通道的图片进行小波变换压缩图片:

R, G, B = cv2.split(img)
# 对三个通道进行小波分解和压缩
four_compress, gzip_csr_size = wavelet_transform((R, G, B), LK, HK)

重点不是小波变换,是小波系数矩阵被我稀疏化后我要把高低频稀疏矩阵用csr表示:

csr_LL = csr_matrix(LL, dtype=np.float32)
csr_LH = csr_matrix(LH, dtype=np.float32)
csr_HL = csr_matrix(HL, dtype=np.float32)
csr_HH = csr_matrix(HH, dtype=np.float32)

这里说明一下,csr_matrix将低频稀疏系数矩阵LL表示成了三个数组(csr_LL里面):data,indices,indptr
然后我用gzip进一步压缩:

compressed_LL = (gzip.compress(csr_LL.data.tobytes()),
                         gzip.compress(csr_LL.indices.tobytes()), gzip.compress(csr_LL.indptr.tobytes()))
compressed_LH = (gzip.compress(csr_LH.data.tobytes()),
                 gzip.compress(csr_LH.indices.tobytes()),gzip.compress(csr_LH.indptr.tobytes()))
compressed_HL = (gzip.compress(csr_HL.data.tobytes()),
                 gzip.compress(csr_HL.indices.tobytes()), gzip.compress(csr_HL.indptr.tobytes()))
compressed_HH = (gzip.compress(csr_HH.data.tobytes()),
                 gzip.compress(csr_HH.indices.tobytes()), gzip.compress(csr_HH.indptr.tobytes()))

好了我通过mqtt协议将压缩好的数据(压缩了至少30%)传输到另一个机器后,我要解压数据恢复成矩阵进行图像分类了。
先gzip解压再将csr格式还原:

data = np.frombuffer(gzip.decompress(compressed_LL[0]))
indices = np.frombuffer(gzip.decompress(compressed_LL[1]))
indptr = np.frombuffer(gzip.decompress(compressed_LL[2]))

# 将data、indices、indptr三个数组转换为CSR格式的稀疏矩阵
sparse = csr_matrix((data,indices,indptr), shape=shape)    # shape是csr格式表示之前的那个矩阵的shape(55,55)
# 将CSR格式转换为原始矩阵格式
dense_LL = sparse.toarray()

没错没错!就是这个坑!!!
问题来了,我的sparse稀疏矩阵一直都是空的!,data,indices,indptr都是0 len。我就纳闷了,我的三个数组不是空的呀怎么到sparse就空了,害得我debug了csr_matrix,然后我就想是不是我没指定数据类型,于是我赶紧添上:

data = np.frombuffer(gzip.decompress(compressed_LL[0]),dtype=np.float32)
indices = np.frombuffer(gzip.decompress(compressed_LL[1]),dtype=np.float32)
indptr = np.frombuffer(gzip.decompress(compressed_LL[2]),dtype=np.float32)

# 将data、indices、indptr三个数组转换为CSR格式的稀疏矩阵
sparse = csr_matrix((data,indices,indptr), shape=shape)    # shape是csr格式表示之前的那个矩阵的shape(55,55)
# 将CSR格式转换为原始矩阵格式
dense_LL = sparse.toarray()

继续空,于是就回到了开头,我说过indices和indptr是int32类型!,我终于误了,就像语言编码一样GBK和utf的转换,他们都是通过字符流编码解码转换的,所以我通过gzip的bytes流压缩解压的时候也要明确对应的数据类型!所以用np.frombuffer的时候一定要明确类型!
最终改为:

data = np.frombuffer(gzip.decompress(compressed_LL[0]),dtype=np.float32)
indices = np.frombuffer(gzip.decompress(compressed_LL[1]),dtype=np.int32)
indptr = np.frombuffer(gzip.decompress(compressed_LL[2]),dtype=np.int32)

# 将data、indices、indptr三个数组转换为CSR格式的稀疏矩阵
sparse = csr_matrix((data,indices,indptr), shape=shape)    # shape是csr格式表示之前的那个矩阵的shape(55,55)
# 将CSR格式转换为原始矩阵格式
dense_LL = sparse.toarray()

可气坏我了

省流: 有空看完,没空看这

原数组压缩时是什么数据类型,解压时需要明确数据类型,因为gzip表示是bytes流表示,你不告诉他几个字节表示一个数据电脑会宕机啦~

# 压缩
compressed = gzip.compress(原数组.tobytes())   # int32类型

# 解压
array = np.frombuffer(gzip.decompress(compressed), dtype=np.int32)

呵呵图片变成这样了
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

Una*

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值