如何改进我的 "rotate (roll / cyclic permutation) array" 解决方案?
How can I improve my "rotate (roll / cyclic permutation) array" solution?
我正在 leetcode 上做一些事情并提出了解决方案它工作正常但有些情况。
这是问题本身:
但在这种情况下它不会:
如果 k 大于数组长度,我如何旋转元素是没有意义的。
如果您有任何改进此解决方案的想法,我将不胜感激
class Solution:
def rotate(self, nums: List[int], k: int) -> None:
"""
Do not return anything, modify nums in-place instead.
"""
if len(nums) > k:
self.swap(nums, 0, len(nums)-1)
self.swap(nums, 0,k-1)
self.swap(nums, k, len(nums)-1)
def swap(self, nums, start, end):
while start < end:
nums[start], nums[end] = nums[end], nums[start]
start+=1
end-=1
为了理解为什么这不适用于 k
大于数组长度的情况,让我尝试解释按 [=11= 这样的值旋转背后的一些逻辑].
模运算符 %
会很有用。例如,如果一个数组的长度为 5,而你想旋转 5,你最终会得到相同的数组。所以从技术上讲,您最好希望旋转 0。这就是 %
运算符发挥作用的地方。 5 % 5 = 0
。如果我们想将一个长度为 5 的数组旋转 7 个点,我们最终会得到与将数组旋转 2 个点相同的结果,结果是 7 % 5 = 2
。你知道我要用这个做什么吗?
如果k
的值小于数组的长度,这也成立。假设我们想要将数组长度旋转 5 乘以 3,我们执行 3 % 5 = 3
。
所以任意旋转量k
和数组长度L
,优化旋转量n
等价于n = k % L
.
你应该在rotate方法的开头修改你的代码来调整旋转量:
k = k % L
并使用此值旋转正确的数量。
迄今为止最快、最干净的解决方案是:
def rotate_right(items, shift):
shift = -shift % len(items)
return items[shift:] + items[:shift]
ll = [i + 1 for i in range(7)]
# [1, 2, 3, 4, 5, 6, 7]
rotate_right(ll, 3)
# [5, 6, 7, 1, 2, 3, 4]
rotate_right([1, 2], 3)
# [2, 1]
当然,不用numpy.roll()
or itertools.cycle()
。
我正在 leetcode 上做一些事情并提出了解决方案它工作正常但有些情况。 这是问题本身:
但在这种情况下它不会:
如果 k 大于数组长度,我如何旋转元素是没有意义的。 如果您有任何改进此解决方案的想法,我将不胜感激
class Solution:
def rotate(self, nums: List[int], k: int) -> None:
"""
Do not return anything, modify nums in-place instead.
"""
if len(nums) > k:
self.swap(nums, 0, len(nums)-1)
self.swap(nums, 0,k-1)
self.swap(nums, k, len(nums)-1)
def swap(self, nums, start, end):
while start < end:
nums[start], nums[end] = nums[end], nums[start]
start+=1
end-=1
为了理解为什么这不适用于 k
大于数组长度的情况,让我尝试解释按 [=11= 这样的值旋转背后的一些逻辑].
模运算符 %
会很有用。例如,如果一个数组的长度为 5,而你想旋转 5,你最终会得到相同的数组。所以从技术上讲,您最好希望旋转 0。这就是 %
运算符发挥作用的地方。 5 % 5 = 0
。如果我们想将一个长度为 5 的数组旋转 7 个点,我们最终会得到与将数组旋转 2 个点相同的结果,结果是 7 % 5 = 2
。你知道我要用这个做什么吗?
如果k
的值小于数组的长度,这也成立。假设我们想要将数组长度旋转 5 乘以 3,我们执行 3 % 5 = 3
。
所以任意旋转量k
和数组长度L
,优化旋转量n
等价于n = k % L
.
你应该在rotate方法的开头修改你的代码来调整旋转量:
k = k % L
并使用此值旋转正确的数量。
迄今为止最快、最干净的解决方案是:
def rotate_right(items, shift):
shift = -shift % len(items)
return items[shift:] + items[:shift]
ll = [i + 1 for i in range(7)]
# [1, 2, 3, 4, 5, 6, 7]
rotate_right(ll, 3)
# [5, 6, 7, 1, 2, 3, 4]
rotate_right([1, 2], 3)
# [2, 1]
当然,不用numpy.roll()
or itertools.cycle()
。