首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >为什么相同的像素使用PIL和Opencv有不同的值?

为什么相同的像素使用PIL和Opencv有不同的值?
EN

Stack Overflow用户
提问于 2019-05-22 10:36:44
回答 2查看 2.5K关注 0票数 4

我从互联网上下载了一张随机图像,然后用PIL.Image.open()cv2.imread()打开它,然后我检查了一些像素的值。问题是,使用PIL和Opencv,我得到了相同像素的不同值!

这就是我试过的图像:

我就是这样做的:

代码语言:javascript
复制
>>> import cv2
>>> from PIL import Image
>>> img = cv2.imread('img.jpg')
>>> im = Image.open('img.jpg')
>>> img[0][0]
>>> array([142, 152, 146], dtype=uint8)
>>> im.getpixel((0, 0))
>>> (138, 158, 131)

R,G,B值(138 != 146),(158 != 152),(131 != 142) imimg不匹配,尽管它是相同的像素和相同的图像!

我查看了这样的帖子,我发现this post在谈论同样的问题,所以我使用了发布的代码再次检查两者之间的差异:

代码语言:javascript
复制
from PIL import Image
import cv2
import sys
from hashlib import md5
import numpy as np

def hashIm(im):
    imP = np.array(Image.open(im))

    # Convert to BGR and drop alpha channel if it exists
    imP = imP[..., 2::-1]
    # Make the array contiguous again
    imP = np.array(imP)
    im = cv2.imread(im)

    diff = im.astype(int)-imP.astype(int)

    cv2.imshow('cv2', im)
    cv2.imshow('PIL', imP)
    cv2.imshow('diff', np.abs(diff).astype(np.uint8))
    cv2.imshow('diff_overflow', diff.astype(np.uint8))

    with open('dist.csv', 'w') as outfile:
        diff = im-imP
        for i in range(-256, 256):
            outfile.write('{},{}\n'.format(i, np.count_nonzero(diff==i)))

    cv2.waitKey(0)
    cv2.destroyAllWindows()

    return md5(im).hexdigest() + '   ' + md5(imP).hexdigest()

if __name__ == '__main__':
    print(hashIm('img.jpg'))

我得到的散列是不同的,而且图像之间的区别也不是黑色的!

附加信息:

  • 操作系统: Ubuntu 18.04
  • Python: 3.6
  • Opencv: opencv-python=4.0.0.21
  • PIL: Pillow==5.4.1

对此有什么解释吗?

EN

回答 2

Stack Overflow用户

发布于 2021-12-14 17:37:11

这可能不是一个数字/舍入问题,而是一个jpg解码变化:https://github.com/python-pillow/Pillow/issues/3833

特别是:

根据维基百科的说法,JPEG解码器可以产生稍微不同的结果,“每个像素分量最多有一点差异”。

(https://github.com/python-pillow/Pillow/issues/3833#issuecomment-585211263)

票数 5
EN

Stack Overflow用户

发布于 2019-05-22 10:59:38

Opencv将图像存储为一条矮胖的ndarray。

代码语言:javascript
复制
import cv2
cv_img = cv2.imread(img_path)
from PIL import Image
pil_img = Image.open(img_path)

当您执行cv_img[x][y]时,您正在访问y第四列和x第四行,但是如果您执行pil_img.getpixel((x,y))枕头访问x第四列和y第四行的像素。

另一个因素是(R, G, B)格式的枕头返回,而opencv则返回(B, G, R)格式。

对我来说,cv_img[20][10]给了array([127, 117, 129], dtype=uint8)。看看这里B = 127G = 117R = 129

但是pil_img[10][20]给了(129, 117, 127)。看看这里R = 129G = 117B = 127

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/56254907

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档