让我们N维像素合并的参考实现/瓢泼大雨对Python的numpy的 [英] Let's make a reference implementation of N-dimensional pixel binning/bucketing for python's numpy

查看:164
本文介绍了让我们N维像素合并的参考实现/瓢泼大雨对Python的numpy的的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我经常想像素斌/桶像素的一个numpy的阵列,意义,更换组 N 与单个像素这是 N 替换像素的总和连续的像素。例如,先从值:

I frequently want to pixel bin/pixel bucket a numpy array, meaning, replace groups of N consecutive pixels with a single pixel which is the sum of the N replaced pixels. For example, start with the values:

x = np.array([1, 3, 7, 3, 2, 9])

为2的桶大小,这转变成

with a bucket size of 2, this transforms into:

bucket(x, bucket_size=2) 
= [1+3, 7+3, 2+9]
= [4, 10, 11]

据我所知,有专门做这个(请纠正我,如果我错了!)没有numpy的功能,所以我经常推出自己。一维数组numpy的,这是不坏:

As far as I know, there's no numpy function that specifically does this (please correct me if I'm wrong!), so I frequently roll my own. For 1d numpy arrays, this isn't bad:

import numpy as np

def bucket(x, bucket_size):
    return x.reshape(x.size // bucket_size, bucket_size).sum(axis=1)

bucket_me = np.array([3, 4, 5, 5, 1, 3, 2, 3])
print(bucket(bucket_me, bucket_size=2)) #[ 7 10  4  5]

...但是,我弄糊涂了轻松多维情况下,我结束了一遍又一遍我自己的滚动车,半称职的解决了这个简单的问题。我喜欢它,如果我们能够建立一个很好的N维参考实现。

...however, I get confused easily for the multidimensional case, and I end up rolling my own buggy, half-assed solution to this "easy" problem over and over again. I'd love it if we could establish a nice N-dimensional reference implementation.


  • preferably函数调用将允许沿不同的轴不同的块大小(或者类似桶(X,bucket_size =(2,2,3))

preferably的解决办法是合理有效的(重塑和金额都在numpy的相当快)

Preferably the solution would be reasonably efficient (reshape and sum are fairly quick in numpy)

积分为处理边缘效应,当阵列没有很好地划分成桶的整数。

Bonus points for handling edge effects when the array doesn't divide nicely into an integer number of buckets.

积分为允许用户选择初始仓边缘偏移。

Bonus points for allowing the user to choose the initial bin edge offset.

正如Divakar建议,这里有一个样品2-D的情况下我的期望行为:

As suggested by Divakar, here's my desired behavior in a sample 2-D case:

x = np.array([[1, 2, 3, 4],
              [2, 3, 7, 9],
              [8, 9, 1, 0],
              [0, 0, 3, 4]])

bucket(x, bucket_size=(2, 2))
= [[1 + 2 + 2 + 3, 3 + 4 + 7 + 9],
   [8 + 9 + 0 + 0, 1 + 0 + 3 + 4]]
= [[8, 23],
   [17, 8]]

...希望我做我自己的算术正确;)

...hopefully I did my arithmetic correctly ;)

推荐答案

我觉得你可以做最有skimage的的 view_as_blocks 。此功能使用实施 as_strided 所以它是非常有效的(它只是改变步幅信息重塑阵列)。因为它是用Python编写/ numpy的,你总是可以复制code,如果你没有安装skimage做的。

I think you can do most of the fiddly work with skimage's view_as_blocks. This function is implemented using as_strided so it is very efficient (it just changes the stride information to reshape the array). Because it's written in Python/NumPy, you can always copy the code if you don't have skimage installed.

应用该功能后,你只需要总结重构阵列的N个轴的联动轴(其中N是 bucket_size 元组的长度)。这里有一个新的斗()功能:

After applying that function, you just need to sum the N trailing axes of the reshaped array (where N is the length of the bucket_size tuple). Here's a new bucket() function:

from skimage.util import view_as_blocks

def bucket(x, bucket_size):
    blocks = view_as_blocks(x, bucket_size)
    tup = tuple(range(-len(bucket_size), 0))
    return blocks.sum(axis=tup)

再例如:

>>> x = np.array([1, 3, 7, 3, 2, 9])
>>> bucket(x, bucket_size=(2,))
array([ 4, 10, 11])

>>> x = np.array([[1, 2, 3, 4],
                  [2, 3, 7, 9],
                  [8, 9, 1, 0],
                  [0, 0, 3, 4]])

>>> bucket(x, bucket_size=(2, 2))
array([[ 8, 23],
       [17,  8]])

>>> y = np.arange(6*6*6).reshape(6,6,6)
>>> bucket(y, bucket_size=(2, 2, 3))
array([[[ 264,  300],
        [ 408,  444],
        [ 552,  588]],

       [[1128, 1164],
        [1272, 1308],
        [1416, 1452]],

       [[1992, 2028],
        [2136, 2172],
        [2280, 2316]]])

这篇关于让我们N维像素合并的参考实现/瓢泼大雨对Python的numpy的的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆