2

我有一个 numpy ndarray,它看起来像:

[[0, 0.25, 1,  ...., 0.5, 0.23 ],
 [0.3, 0.75, 1, ..., 0.5, 0.37 ],
  ...,
  ...,
 [0, 0.25, 1,  ...., 0.5, 0.23 ],
 [0.3, 0.75, 1, ..., 0.5, 0.37 ]]

基本上每个值都在 0 - 1.0 范围内

我想将其可视化为位图,目前我有一个非常慢的循环,基本上是这样做的:

for i, row in enumerate(data):
    for j, val in enumerate(row):
        yield val_to_rgb(val)

然后它将采用 rgb 组件的 3 元组并对其执行 PIL putdata 并创建一个 PNG。

我需要这样做很多次,这种 ghetto 方法很慢,而且着色非常难看。

我的问题是这样的:

我可以应用一系列矩阵运算来生成包含原始 RGB 值的彩色矩阵吗?

这实际上包括两个问题:

  1. 我可以应用什么最有效的转换来从上述矩阵中获取 RGB 元组
  2. 有没有一种“好”的方法可以将 (0, 1.0) 值转换为彩色表示?

编辑:澄清-我希望将其保存为 PNG,而不仅仅是实时查看。原因是其中很多都是在无头机器上执行的,然后我会在事后对其进行检查。

当前算法的输出看起来很糟糕:

彩色矩阵

4

2 回答 2

3

matplotlib 具有imshow功能,您可以开箱即用。

您所做的通常是通过“矢量化”完成的。您定义一个函数并让 numpy 进行迭代:

vec = np.vectorize(val_to_rgb)
rgb_data = vec(data)
于 2012-12-25T16:28:25.850 回答
2

我对 PIL 不是很熟悉,但我猜它会吞下一个 numpy 形状的数组(rows, cols, 3)并将其变成图像。因此,您想重写您的val_to_rgb函数,使其适用于数组,而不是标量,并将 RGB 值放在形状的最后一维中。

例如,假设您想将值解释为灰度,0 表示黑色,1 表示白色。您当前采用标量输入的函数如下所示:

def val_to_rgb(val) :
    return (int(val * 255),) * 3

向量化的形式类似于:

def vals_to_rgbs(vals) :
    ret = np.zeros(vals.shape + (3,),  dtype='uint8')
    ret[...] = vals.reshape(vals.shape + (1,)) * 255
    return ret

>>> vals_to_rgb(np.random.rand(10,10)).shape
(10, 10, 3)
>>> vals_to_rgb(np.random.rand(10,10)).dtype
dtype('uint8')

重塑是让广播发挥它的魔力。

Thinks can get more complicated, so if you need help vectorizing your specific val_to_rgb function, post your code and I'll gladly take a shot at it.

于 2012-12-25T16:50:31.340 回答