@@ -61,9 +61,15 @@ https://leetcode-cn.com/problems/capacity-to-ship-packages-within-d-days/
61
61
62
62
## 思路
63
63
64
+ 题目给定了 weights 长度 <= 50000,因此大概就可以锁定为 nlogn 解法。为啥?大家可以看下我的插件就知道了。另外我的插件还提供了多种规模的复杂度速查表。地址:https://leetcode-pp.github.io/leetcode-cheat/?tab=data-structure-vis
65
+
66
+ ![ ] ( https://tva1.sinaimg.cn/large/008i3skNly1gpwyi1zhc0j30mm0h2757.jpg )
67
+
64
68
这道题和[ 猴子吃香蕉] ( https://github.com/azl397985856/leetcode/blob/master/problems/875.koko-eating-bananas.md ) 简直一摸一样,没有看过的建议看一下那道题。
65
69
66
- 像这种题如何你能发现本质的考点,那么 AC 是瞬间的事情。 这道题本质上就是从 1,2,3,4,。。。total(其中 toal 是总的货物重量)的有限离散数据中查找给定的数。这里我们不是直接查找 target,而是查找恰好能够在 D 天运完的载货量。
70
+ 这种题都是简单的能力检测二分,如果不懂的,建议看下西法之前写过的二分专题,写的可详细了。
71
+
72
+ 像这种题如何你能发现本质的考点,那么 AC 是瞬间的事情。 这道题本质上就是从 1,2,3,4,。。。total(其中 toal 是总的货物重量)的有限离散数据中查找给定的数。这里我们不是直接查找 target,而是查找恰好能够在 D 天** 内** 运完的载货量。
67
73
68
74
- 容量是 1 可以运完么?
69
75
- 容量是 2 可以运完么?
@@ -79,20 +85,22 @@ https://leetcode-cn.com/problems/capacity-to-ship-packages-within-d-days/
79
85
def canShip (opacity ):
80
86
# 指定船的容量是否可以在D天运完
81
87
lo = 0
82
- hi = total
83
- while lo < hi:
88
+ hi = total # total 其实就是 sum(weights)
89
+ while lo <= hi:
84
90
mid = (lo + hi) // 2
85
91
if canShip(mid):
86
- hi = mid
92
+ hi = mid - 1
87
93
else :
88
94
lo = mid + 1
89
95
90
96
return lo
91
97
```
92
98
99
+ 这其实就是我二分专题里的** 最左二分** ,大家直接套这个模板就行了。
100
+
93
101
## 关键点解析
94
102
95
- - 能够识别出是给定的有限序列查找一个数字(二分查找),要求你对二分查找以及变体十分熟悉
103
+ - 能力检测二分
96
104
97
105
## 代码
98
106
@@ -103,34 +111,31 @@ Python Code:
103
111
``` python
104
112
class Solution :
105
113
def shipWithinDays (self , weights : List[int ], D : int ) -> int :
106
- lo = 0
107
- hi = 0
108
-
109
- def canShip (opacity ):
114
+ def possible (mid ):
110
115
days = 1
111
- remain = opacity
112
- for weight in weights:
113
- if weight > opacity :
116
+ cur = 0
117
+ for w in weights:
118
+ if w > mid :
114
119
return False
115
- remain -= weight
116
- if remain < 0 :
120
+ if cur + w > mid:
121
+ cur = 0
117
122
days += 1
118
- remain = opacity - weight
123
+ cur += w
119
124
return days <= D
120
125
121
- for weight in weights:
122
- hi += weight
123
- while lo < hi :
124
- mid = (lo + hi ) // 2
125
- if canShip (mid):
126
- hi = mid
126
+ l, r = 1 , sum ( weights)
127
+
128
+ while l <= r :
129
+ mid = (l + r ) // 2
130
+ if possible (mid):
131
+ r = mid - 1
127
132
else :
128
- lo = mid + 1
133
+ l = mid + 1
134
+ return l
129
135
130
- return lo
131
136
```
132
137
133
- js Code:
138
+ JS Code:
134
139
135
140
``` js
136
141
/**
@@ -176,5 +181,15 @@ var shipWithinDays = function (weights, D) {
176
181
177
182
** 复杂度分析**
178
183
179
- - 时间复杂度:$O(logN)$
180
- - 空间复杂度:$O(N)$
184
+ 令 n 为 weights 长度。
185
+
186
+ - 时间复杂度:$O(nlogn)$
187
+ - 空间复杂度:$O(1)$
188
+
189
+ > 此题解由 [ 力扣刷题插件] ( https://leetcode-pp.github.io/leetcode-cheat/?tab=solution-template ) 自动生成。
190
+
191
+ 力扣的小伙伴可以[ 关注我] ( https://leetcode-cn.com/u/fe-lucifer/ ) ,这样就会第一时间收到我的动态啦~
192
+
193
+ 以上就是本文的全部内容了。大家对此有何看法,欢迎给我留言,我有时间都会一一查看回答。更多算法套路可以访问我的 LeetCode 题解仓库:https://github.com/azl397985856/leetcode 。 目前已经 40K star 啦。大家也可以关注我的公众号《力扣加加》带你啃下算法这块硬骨头。
194
+
195
+ 关注公众号力扣加加,努力用清晰直白的语言还原解题思路,并且有大量图解,手把手教你识别套路,高效刷题。
0 commit comments