我正在尝试将单个 1D numpy 数组中的多个不重叠的切片提取到 2D 数组的连续行中。
假设源数组是,
s=array([0, 1, 2, 3, 4, 5, 6, 7, 9, 10, 11, 12])
目标数组是一个由零组成的二维数组,例如,
t = array([[0, 0, 0, 0, 0],
[0, 0, 0, 0, 0]])
我想从
[1:4:1]
中提取切片[6:10:1]
和s
并将它们注入到t
中。 s
中的切片数量与 t
中的行数一样多。所有切片都比 t
的行长短。每个提取的切片应替换 t
中相应行的值。
t
的期望结果是:
array([[1, 2, 3, 0, 0],
[6, 7, 8, 9, 0]])
如果提取的切片的长度都相等,那么我可以使用 2D 索引数组来完成此操作,但它们不是。
我怀疑我应该能够通过创建两个切片数组来做到这一点。其中一个定义从源中选择数据的切片,另一个确定目标行位置,然后使用类似的内容,
b[:,target_slice_array]=a[source_slice_array]
但我就是想不出任何有效的语法。
这是我目前正在使用的简单循环方法。这就是我正在努力加快的速度。
source=np.array([0, 1, 2, 3, 4, 5, 6, 7, 9, 10, 11, 12])
source_slices=[np.s_[0:2:1], np.s_[7:10:1]]
target_slices=[np.s_[0:2:1], np.s_[0:3:1]]
target=np.zeros(shape=(2,10), dtype=np.int32)
#for index, (source_slice, target_slice) in enumerate(zip(source_slices, target_slices)):
#target[index,target_slice]=source[source_slice]
# Doubles the speed by moving the for loop to use range
for index in range(len(source_slices)):
target[index,target_slices[index] = source[source_slices[index]]
这会将目标更新为,
[[ 0 1 0 0 0 0 0 0 0 0]
[ 7 9 10 0 0 0 0 0 0 0]]
以下内容不是很好,而且几乎肯定比小输入的速度慢,但它是完全矢量化的,如果满足以下条件,可能值得这样做:
在所有情况下,您都需要使用真实的数据进行基准测试。
import numpy as np
source = np.arange(13)
source_start = np.array((0, 7, 3))
source_stop = np.array((2, 10, 10))
lengths = source_stop - source_start
target_start = np.array((0, 5, 2))
target_stop = target_start + lengths
target_width = 10
to_repeat = source_start.copy()
to_repeat[1:] -= lengths[:-1].cumsum()
idx = to_repeat.repeat(lengths)
idx += np.arange(idx.size)
target = np.zeros(shape=(source_start.size, target_width), dtype=source.dtype)
x = np.arange(target_width)
target_mask = (x >= target_start[:, np.newaxis]) & (x < target_stop[:, np.newaxis])
target[target_mask] = source[idx]
print(target)
[[0 1 0 0 0 0 0 0 0 0]
[0 0 0 0 0 7 8 9 0 0]
[0 0 3 4 5 6 7 8 9 0]]