计算图像中不同颜色的面积比

Calculate the ratio of area of different colors in an image

我正在尝试计算图像中颜色的比例,return 这是一个比率。我有很多 "logs" 的图像,它们是颜色的垂直序列,我想知道一种颜色的总面积与另一种颜色的差异,以及一种颜色相对于整个图像的比率.

举个例子,在下图中,如果我计算蓝色占据的总面积并将其与整个面积(蓝色和棕色相结合,我得到比率 = 69.14。(我得到那个值通过将所有蓝色矩形的面积相加并除以所有蓝色和棕色矩形的总面积)

*注意,颜色不会总是下面的颜色,如果可能的话,我希望能够使用两种以上的颜色(也许只给出我正在使用的颜色的 RGB 代码)专注于并希望该颜色与整个颜色的比例)。

请注意,我有很多图像,我必须 运行 这一张,所以如果可能的话,循环遍历文件夹中的所有图像会很有帮助。

我根据几个例子拼凑成下面的代码,但我对一些事情感到困惑。第一,除非必须,否则我不一定要将图像转换为二进制;第二,看起来我正在计算白色像素而不是黑色像素的数量。不确定我哪里出错了。

import cv2
import numpy as np 
from matplotlib import pyplot as plt

# load image
image = cv2.imread('/Users/Me/Desktop/logtest.png',0)

# plot the binary image
imgplot = plt.imshow(image, "gray")
plt.show()

#Calculate percent of pixels that are black
ret,thresh = cv2.threshold(image,0,230, cv2.THRESH_BINARY)
height, width = image.shape

print ("Height and Width : ",height, width)
size = image.size

print ("Total number of pixels in the image is =", size)

ChosenPix = cv2.countNonZero(image)
print("Total number of black pixels =", count)

Ratio = (ChosenPix/size)*100
print("Ratio of black to total is =", Ratio)

我制作了一些这样的示例图片:

然后我使用 glob 来 select 所有名为 log*png 的文件并处理每个文件。这包括计算图像中的独特颜色并迭代这些颜色以计算与每种独特颜色匹配的像素数:

#!/usr/bin/env python3

from PIL import Image
import numpy as np
import glob

def processLog(filename):
    print(f"Processing log: {filename}")
    # Open this image and make a Numpy version for easy processing
    im   = Image.open(filename).convert('RGBA').convert('RGB')
    imnp = np.array(im)
    h, w = imnp.shape[:2]

    # Get list of unique colours...
    # Arrange all pixels into a tall column of 3 RGB values and find unique rows (colours)
    colours, counts = np.unique(imnp.reshape(-1,3), axis=0, return_counts=1)

    # Iterate through unique colours
    for index, colour in enumerate(colours):
        count = counts[index]
        proportion = (100 * count) / (h * w)
        print(f"   Colour: {colour}, count: {count}, proportion: {proportion:.2f}%")

# Iterate over all images called "log*png" in current directory
for filename in glob.glob('log*png'):
    processLog(filename)

输出

Processing log: log2.png
   Colour: [  0 255 255], count: 800, proportion: 5.00%
   Colour: [255   0 255], count: 6400, proportion: 40.00%
   Colour: [255 255   0], count: 8800, proportion: 55.00%
Processing log: log1.png
   Colour: [  0 255   0], count: 6400, proportion: 36.36%
   Colour: [255   0   0], count: 11200, proportion: 63.64%
Processing log: log9.png
   Colour: [ 83 195 187], count: 16160, proportion: 67.33%
   Colour: [ 87 190 179], count: 80, proportion: 0.33%
   Colour: [ 88 184 171], count: 80, proportion: 0.33%
   Colour: [ 89 180 165], count: 80, proportion: 0.33%
   Colour: [ 94 175 158], count: 80, proportion: 0.33%
   Colour: [ 96 164 143], count: 80, proportion: 0.33%
   Colour: [107 146 116], count: 80, proportion: 0.33%
   Colour: [120 114  71], count: 80, proportion: 0.33%
   Colour: [124  99  50], count: 80, proportion: 0.33%
   Colour: [126  88  35], count: 7120, proportion: 29.67%
   Colour: [126  90  37], count: 80, proportion: 0.33%

当然,如果你不想写任何Python,你可以在bash循环中遍历文件并使用ImageMagick 为您提取总像素数和每种颜色的像素数。 ImageMagick 安装在大多数 Linux 发行版上,可用于 macOS 和 Windows:

for f in log*png; do magick "$f" -format "%f: %[fx:w*h]\n"  -write info: -format %c histogram:info: ; done

输出

log1.png: 17600
      6400: (  0,255,  0) #00FF00 lime
     11200: (255,  0,  0) #FF0000 red
log2.png: 16000
       800: (  0,255,255) #00FFFF cyan
      6400: (255,  0,255) #FF00FF magenta
      8800: (255,255,  0) #FFFF00 yellow
log9.png: 24000
     16160: ( 83,195,187,255) #53C3BBFF srgba(83,195,187,1)
        80: ( 87,190,179,255) #57BEB3FF srgba(87,190,179,1)
        80: ( 88,184,171,251) #58B8ABFB srgba(88,184,171,0.984314)
        80: ( 89,180,165,255) #59B4A5FF srgba(89,180,165,1)
        80: ( 94,175,158,246) #5EAF9EF6 srgba(94,175,158,0.964706)
        80: ( 96,164,143,255) #60A48FFF srgba(96,164,143,1)
        80: (107,146,116,246) #6B9274F6 srgba(107,146,116,0.964706)
        80: (120,114, 71,246) #787247F6 srgba(120,114,71,0.964706)
        80: (124, 99, 50,255) #7C6332FF srgba(124,99,50,1)
      7120: (126, 88, 35,255) #7E5823FF srgba(126,88,35,1)
        80: (126, 90, 37,250) #7E5A25FA srgba(126,90,37,0.980392)