-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy path134 Gas Station.py
65 lines (52 loc) · 2.29 KB
/
134 Gas Station.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
"""
There are N gas stations along a circular route, where the amount of gas at station i is gas[i].
You have a car with an unlimited gas tank and it costs cost[i] of gas to travel from station i to its next station
(i+1). You begin the journey with an empty tank at one of the gas stations.
Return the starting gas station's index if you can travel around the circuit once, otherwise return -1.
Note:
The solution is guaranteed to be unique.
Author: Rajeev Ranjan
"""
class Solution:
def canCompleteCircuit(self, gas, cost):
"""
.-''''-.
|== ==|-.
|~~ ~~~|`\\
| FUEL | ||
| |//
| |/
| |
__|______|__
[____________]
Algorithm:
Similar to maximum sub-array problem
1. determine whether can cover one cycle
2. determine the start_index:
define: sum[i, j] = sum(diff[k]) for i<=k<j
start testing from i, sum[i, i+1]>0, iterate until reach j such that sum[i, j-1]>0, sum[i, j]<0, then do you
need to go back to i+1? No, since sum[i, i+1]>0, you are better off starting from i with some gas left rather
than i+1 with absolute 0 gas in the car. Do you need to go back to i+2? No, since sum[i, i+2]>0. Similarly,
you do not need to start from i+3, i+4, ..., j. You only need to start the testing from j+1.
:param gas: a list of integers
:param cost: a list of integers, cost[i] from i to i+1
:return: an integer
"""
length = len(gas)
# gas difference
diff = [gas[i]-cost[i] for i in xrange(length)]
# find whether can cover one cycle
# starting from arbitrary point
if sum(diff)<0:
return -1
# find the starting index
start_index = 0
sum_before = 0
for ind, val in enumerate(diff): # O(N), rather than brutal force O(N^2)
sum_before += val
if sum_before<0: # reset sum_before since gas insufficient for the journey. # sum[i, j]<0
start_index = ind+1
sum_before = 0
return start_index
if __name__=="__main__":
Solution().canCompleteCircuit([5], [4])