【问题标题】:Sort image as NP array将图像排序为 NP 数组
【发布时间】:2021-05-26 23:45:15
【问题描述】:

我正在尝试使用我不熟悉的 NumPy 按亮度对图像进行排序。我设法创建了一个随机图像并对其进行排序。

def create_image(output, width, height, arr):

  array = np.zeros([height, width, 3], dtype=np.uint8)

  numOfSwatches = len(arr)
  swatchWidth = int(width/ numOfSwatches)

  for i in range (0, numOfSwatches):
    m = i * swatchWidth
    r = (i+1) * swatchWidth 
    array[:, m:r] = arr[i]

  img = Image.fromarray(array)
  img.save(output)

创建此图像:

到目前为止一切顺利。只是现在我想从创建随机图像切换到加载它们并然后对它们进行排序。

#!/usr/bin/python3

import numpy as np
from PIL import Image

# --------------------------------------------------------------
def load_image( infilename ) :
  img = Image.open( infilename )
  img.load()
  data = np.asarray( img, dtype = "int32" )
  return data

# --------------------------------------------------------------
def lum (r,g,b):
 return math.sqrt( .241 * r + .691 * g + .068 * b )


myImageFile = "random_colours.png"
imageNP = load_image(myImageFile)
imageNP.sort(key=lambda rgb: lum(*rgb) )

图像应如下所示:

我得到的错误是 TypeError: 'key' is an invalid keyword argument for this function 我可能错误地创建了 NP 数组,因为它是一个随机 NP 数组。

【问题讨论】:

    标签: python numpy colors python-imaging-library


    【解决方案1】:

    从未使用过 PIL,但希望以下方法有效(我不确定,因为我无法重现您的确切示例),当然可能有更有效的方法可以做到这一点。 我正在使用您的函数,已将 lum 函数中的 math.sqrt 函数更改为 np.sqrt - 因为它更适合矢量计算。顺便说一句,我相信这不适用于 int32 类型的数组(如在您的 load_image 函数中)。

    关键部分是 Numpy 的 argsort 函数(最后一行),它给出了对给定数组进行排序的索引;这应用于光度数组的一行(利用 simmetry),后来用作img_array 的索引器。

    # Create random image
    np.random.seed(4)
    img = create_image('test.png', 75, 75, np.random.random((25,3))*255)
    # Convert to Numpy array and calculate luminosity
    img_array  = np.array(img, dtype = np.uint8)
    luminosity = lum(img_array[...,0], img_array[...,1], img_array[...,2])
    # Sort by luminosity and convert to image again
    img_sorted = Image.fromarray(img_array[:,luminosity[0].argsort()])
    

    原图:

    还有亮度排序的:

    【讨论】:

    • 现在更清楚了!!无法从第一篇文章中猜到 arr(也错过了导入数学)
    • ''....在 lum 函数中将 math.sqrt 函数更改为 np.sqrt - 因为它更适合向量计算。 ....''我会说不是更好,而是让它发挥作用的唯一方法!正如 math.sqrt 给出的那样: return math.sqrt( .241 * r + .691 * g + .068 * b ) TypeError: only size-1 arrays can be convert to Python scalars
    • @pippo1980,是的,我不确定,但它只适用于标量。
    • 是的,现在我需要弄清楚标量是什么:-)
    • 怎么样 lum(img_array[...,0] .... 意思是三个点 [...,0] ?不确定它们在 python 中代表什么?我会猜到一些东西比如:,:,0?
    猜你喜欢
    • 2023-01-23
    • 2021-07-08
    • 1970-01-01
    • 2019-01-09
    • 2021-11-08
    • 1970-01-01
    • 2018-08-28
    • 2017-03-21
    • 1970-01-01
    相关资源
    最近更新 更多