问题描述
小R有一个特殊的随机播放规则。他首先播放歌单中的第一首歌,播放后将其从歌单中移除。如果歌单中还有歌曲,则会将当前第一首歌移到最后一首。这个过程会一直重复,直到歌单中没有任何歌曲。
例如,给定歌单[5,3,2,1,4],真实的播放顺序是[5,2,4,1,3]。 保证歌曲中的id两两不同
测试样例
样例1:
输入: n = 5 ,a = [5,3,2,1,4]输出:[5,2,4,1,3]
样例2:
输入: n = 4 ,a = [4,1,3,2]输出: [4,3,1,2]
样例3:
输入: n = 6 ,a = [1,2,3,4,5,6]输出: [1,3,5,2,6,4]
问题理解
题目描述了一个特殊的随机播放规则:
- 首先播放歌单中的第一首歌,并将其从歌单中移除。
- 如果歌单中还有歌曲,则将当前第一首歌移到最后一首。
- 重复上述过程,直到歌单中没有任何歌曲。
数据结构选择
我们可以使用一个队列(Queue)来模拟这个过程:
- 队列的特性是先进先出(FIFO),非常适合用来处理这种顺序播放和移动的操作。
算法步骤
-
初始化:将歌单中的所有歌曲放入队列。
-
播放歌曲:
- 从队列中取出第一首歌,并将其加入结果列表。
- 如果队列中还有歌曲,则将当前队列的第一首歌移到队列的末尾。
-
重复:重复上述步骤,直到队列为空。
from collections import deque def solution(n: int, a: list) -> list: # 使用deque初始化队列,deque的popleft和append操作时间复杂度为O(1) queue = deque(a) result = [] while queue: # 播放当前队列中的第一首歌 song = queue.popleft() result.append(song) # 如果队列中还有其他歌曲,将当前播放的歌曲移到队列末尾 if queue: queue.append(queue.popleft()) return result # 测试 if __name__ == '__main__': print(solution(n = 5, a = [5, 3, 2, 1, 4]) == [5, 2, 4, 1, 3]) print(solution(n = 4, a = [4, 1, 3, 2]) == [4, 3, 1, 2]) print(solution(n = 6, a = [1, 2, 3, 4, 5, 6]) == [1, 3, 5, 2, 6, 4])
时间复杂度:
- 每次
popleft()和append()都是 O(1) 操作,而队列中有n个元素,因此时间复杂度为 O(n)。
总结:
- 通过使用
deque,代码的性能得到了提升,尤其在处理较大输入时。