解法
还是不到家,两个思路都想到了但是一个浪费空间一个没想透彻= =
解法一:DP
肯定不能把油量作为dp的下标,所以我们考虑dp[i][j]
,表示到达车站i
,加了j
次油时剩余的最大油量。注意,我们考虑的是在车站i-1
加不加油。
令车站i
和车站i-1
之间的距离为dis
- 假如不加油,那么到达车站
i
时候的最大油量为:dp[i-1][j]-dis
- 假如加油,那么到达车站
i
时候的最大油量为:max(-1, dp[i-1][j-1]+Fuel[i-1]-dis)
,注意只有dp[i-1][j-1]
非负时可以这么算。
否则由于i-1车站只加j-1次油是到不了的,所以不可能在车站i-1
再加油
状态转移方程为:
d
p
[
i
]
[
j
]
=
{
max
(
−
1
,
d
p
[
i
−
1
]
[
j
]
−
d
i
s
,
d
p
[
i
−
1
]
[
j
−
1
]
+
F
u
e
l
[
i
−
1
]
−
d
i
s
)
,
j
>
0
and
d
p
[
i
−
1
]
[
j
−
1
]
≥
0
max
(
−
1
,
d
p
[
i
−
1
]
[
j
]
−
d
i
s
)
,
j
=
=
0
or
d
p
[
i
−
1
]
[
j
−
1
]
<
0
dp[i][j] = \left\{\begin{matrix} \max(-1, dp[i-1][j]-dis, dp[i-1][j-1]+Fuel[i-1]-dis) & , j>0\text{ and }dp[i-1][j-1]\ge 0\\ \max(-1, dp[i-1][j]-dis) & , j==0\text{ or }dp[i-1][j-1]< 0\\ \end{matrix}\right.
dp[i][j]={max(−1,dp[i−1][j]−dis,dp[i−1][j−1]+Fuel[i−1]−dis)max(−1,dp[i−1][j]−dis),j>0 and dp[i−1][j−1]≥0,j==0 or dp[i−1][j−1]<0
观察一下状态转移方程,跟背包问题一样,是可以空间优化,从而把i这一维给去掉的。
最后只要找到最小的j,使得dp[j]非负就行了
class Solution(object):
def minRefuelStops(self, target, startFuel, stations):
"""
:type target: int
:type startFuel: int
:type stations: List[List[int]]
:rtype: int
"""
stations.append([target,0])
n = len(stations)
dp = [-1]*(n+1)
dp[0] = startFuel-stations[0][0] if startFuel>=stations[0][0] else -1
for i in xrange(1, n):
for j in xrange(i+1, -1, -1):
dis = stations[i][0]-stations[i-1][0]
dp[j] = dp[j]-dis
if j>0 and dp[j-1]>=0:
dp[j] = max(dp[j-1]+stations[i-1][1]-dis, dp[j])
dp[j] = max(-1, dp[j])
l = 0
r = n-1
while r>l:
mid = (r+l)>>1
if dp[mid]>=0:
r = mid
else:
l = mid+1
return r if dp[r]>=0 else -1
解法二:堆
一开始我想过贪心法,就是先能走多远走多远,缺油了就找经过的最大的车站加油然后再走。不过当时脑子傻了,最大的加完也走不到会出错,然后就转投了DP的怀抱= =
其实可以一直加,加到能走到下一个站点为止,用最大堆就可以了
class Solution(object):
def minRefuelStops(self, target, startFuel, stations):
"""
:type target: int
:type startFuel: int
:type stations: List[List[int]]
:rtype: int
"""
stations.append([target,0])
n = len(stations)
ans = 0
from heapq import heappush, heappop
pq = []
for place, fuel in stations:
while startFuel<place and len(pq):
startFuel -= heappop(pq)
ans += 1
if startFuel<place:
return -1
heappush(pq, -fuel)
return ans
卧槽,快了一个数量级……