当前位置: 代码迷 >> 综合 >> AcWing 单调队列优化DP问题 1088. 旅行问题
  详细解决方案

AcWing 单调队列优化DP问题 1088. 旅行问题

热度:8   发布时间:2024-02-05 15:04:15.0
import sys
sys.stdin = open('data.txt', 'r')'''
问题做一下转换,把环拆开,组成长度为原来两倍的序列,把每个车站的油量和下一步的距离的差值
作为数组元素的数值,对这个长度是2n的数组求前缀和序列,其实题目要求的就是所有长度是n的滑动
窗口里面前缀和的最小值和窗口开始位置前面一个前缀和的差值的最小值是不是小于0,如果小于0,
说明中间n次移动至少有一次出现了没有油的情况,顺时针和逆时针都做一遍单调队列求滑动窗口最小值
的流程,两次结果有一次是成功的,就可以从该位置绕一圈回到原点
'''arr = []
n = int(input())
flag = [0] * nl = []
for _ in range(n):a, b = map(int, input().split())l.append((a, b))arr.append(a-b)arr =  arr * 2
for i in range(1, 2*n):arr[i] += arr[i-1]# 求长度为n的滑动窗口中的极小值
from collections import deque# 顺时针
que = deque()
for idx, val in enumerate(arr):base_val = arr[idx-n] if idx >= n else 0while len(que) > 0 and idx - que[0][0] >= n:que.popleft()while len(que) > 0 and val <= que[-1][1]:que.pop()que.append((idx, val))if idx >= n-1 and idx < 2*n-1:if que[0][1] - base_val >= 0:flag[idx - (n-1)] += 1arr = []
for i in range(n):arr.append(l[i][0] - l[i-1][1])arr = arr[::-1]
arr =  arr * 2
for i in range(1, 2*n):arr[i] += arr[i-1]# 逆时针
que = deque()
for idx, val in enumerate(arr):base_val = arr[idx-n] if idx >= n else 0while len(que) > 0 and idx - que[0][0] >= n:que.popleft()while len(que) > 0 and val <= que[-1][1]:que.pop()que.append((idx, val))if idx >= n-1 and idx < 2*n-1:if que[0][1] - base_val >= 0:flag[2*(n-1) - idx] += 1for f in flag:print('TAK' if f > 0 else 'NIE')