【问题标题】:What's an efficient way to shift a range of items left or right within an 1d NumPy array?在 1d NumPy 数组中向左或向右移动一系列项目的有效方法是什么?
【发布时间】:2020-07-27 00:44:38
【问题描述】:

假设我有一个这样的数组:

arr = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

我想向左或向右移动给定范围的项目。例如,从位置 4 开始向右移动 3 个位置:

>>> shift(arr, 4, 3)
arr = [0, 1, 2, 3, 4, 5, 6, 4, 5, 6, 7]

或从位置 4 开始移动,但向左移动:

>>> shift(arr, 4, -3)
arr = [0, 4, 5, 6, 4, 5, 6, 7, 5, 6, 7]

我将原始项目留在原处,但不管是什么留在该范围项目所在的原始位置。可能是零或其他任何东西 - 无论如何我都会覆盖它。

我对 NumPy 很陌生,但我认为可能有一些切片语法可以用 NumPy 完成此任务,但我无法想出如何完成此任务。

另一种方法是循环并逐个复制项目,但我希望有一种更有效/更优雅的方式来做到这一点。

感谢任何帮助!

【问题讨论】:

  • 元素移出数组边界会怎样?
  • 是的,您可以为此使用基本切片,它只是在 C 代码中执行“替代”循环。您必须做一些数学运算才能弄清楚您正在使用哪些索引来编写以及您想要覆盖哪些索引,并且在这种情况下它们必须具有相同的长度。一般来说,将一个数组分配给另一个数组的基本切片需要兼容的广播形状(看看这个,它真的很有帮助)。
  • @Marat 它不会 - 我正在操作一个保证足够大以适应转变的大型阵列。

标签: python arrays numpy python-3.7


【解决方案1】:

您需要提取要移动的数组部分(从position 到数组末尾减去移动量(如果为正数)),然后从新位置替换数组部分(position + shift) 与提取的部分。这将保留原始值。

def shift(arr, pos, amt):
    arrv = arr[pos:min(len(arr)-amt, len(arr))]
    arr[pos+amt:pos+amt+len(arrv)] = arrv
    
arr = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

shift(arr, 4, 3)
print(arr)
shift(arr, 4, -3)
print(arr)

输出:

[0, 1, 2, 3, 4, 5, 6, 4, 5, 6, 7]
[0, 4, 5, 6, 4, 5, 6, 7, 5, 6, 7]

【讨论】:

  • 谢谢你,这正是我想要的,你的回答实际上帮助我理解了切片在 python 中的工作原理。
  • @EdyBourne 不用担心 - 我很高兴能提供帮助。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-10-29
  • 1970-01-01
  • 2017-11-22
  • 1970-01-01
相关资源
最近更新 更多