Skip to content

Commit f9bb656

Browse files
committed
feat: add solutions to lc problem: No.1167
No.1167.Minimum Cost to Connect Sticks
1 parent ea9aa78 commit f9bb656

File tree

7 files changed

+369
-137
lines changed

7 files changed

+369
-137
lines changed

solution/1100-1199/1167.Minimum Cost to Connect Sticks/README.md

Lines changed: 129 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,13 @@
5858

5959
<!-- 这里可写通用的实现逻辑 -->
6060

61-
优先队列。
61+
**方法一:贪心 + 优先队列(小根堆)**
62+
63+
我们可以使用贪心的思路,每次选择最短的两根棍子进行拼接,这样可以保证拼接的代价最小。
64+
65+
因此,我们可以使用优先队列(小根堆)来维护当前棍子的长度,每次从优先队列中取出两根棍子进行拼接,再将拼接后的棍子放回优先队列中,直到优先队列中只剩下一根棍子为止。
66+
67+
时间复杂度 $O(n \times \log n)$,空间复杂度 $O(n)$。其中 $n$ 是数组 `sticks` 的长度。
6268

6369
<!-- tabs:start -->
6470

@@ -69,15 +75,13 @@
6975
```python
7076
class Solution:
7177
def connectSticks(self, sticks: List[int]) -> int:
72-
h = []
73-
for s in sticks:
74-
heappush(h, s)
75-
res = 0
76-
while len(h) > 1:
77-
val = heappop(h) + heappop(h)
78-
res += val
79-
heappush(h, val)
80-
return res
78+
heapify(sticks)
79+
ans = 0
80+
while len(sticks) > 1:
81+
z = heappop(sticks) + heappop(sticks)
82+
ans += z
83+
heappush(sticks, z)
84+
return ans
8185
```
8286

8387
### **Java**
@@ -88,16 +92,16 @@ class Solution:
8892
class Solution {
8993
public int connectSticks(int[] sticks) {
9094
PriorityQueue<Integer> pq = new PriorityQueue<>();
91-
for (int s : sticks) {
92-
pq.offer(s);
95+
for (int x : sticks) {
96+
pq.offer(x);
9397
}
94-
int res = 0;
98+
int ans = 0;
9599
while (pq.size() > 1) {
96-
int val = pq.poll() + pq.poll();
97-
res += val;
98-
pq.offer(val);
100+
int z = pq.poll() + pq.poll();
101+
ans += z;
102+
pq.offer(z);
99103
}
100-
return res;
104+
return ans;
101105
}
102106
}
103107
```
@@ -109,51 +113,130 @@ class Solution {
109113
public:
110114
int connectSticks(vector<int>& sticks) {
111115
priority_queue<int, vector<int>, greater<int>> pq;
112-
for (int x : sticks) pq.push(x);
113-
int res = 0;
116+
for (auto& x : sticks) {
117+
pq.push(x);
118+
}
119+
int ans = 0;
114120
while (pq.size() > 1) {
115-
int val = pq.top();
121+
int x = pq.top();
116122
pq.pop();
117-
val += pq.top();
123+
int y = pq.top();
118124
pq.pop();
119-
res += val;
120-
pq.push(val);
125+
int z = x + y;
126+
ans += z;
127+
pq.push(z);
121128
}
122-
return res;
129+
return ans;
123130
}
124131
};
125132
```
126133
127134
### **Go**
128135
129136
```go
130-
func connectSticks(sticks []int) int {
131-
h := IntHeap(sticks)
132-
heap.Init(&h)
133-
res := 0
134-
for h.Len() > 1 {
135-
val := heap.Pop(&h).(int)
136-
val += heap.Pop(&h).(int)
137-
res += val
138-
heap.Push(&h, val)
137+
func connectSticks(sticks []int) (ans int) {
138+
hp := &hp{sticks}
139+
heap.Init(hp)
140+
for hp.Len() > 1 {
141+
x, y := heap.Pop(hp).(int), heap.Pop(hp).(int)
142+
ans += x + y
143+
heap.Push(hp, x+y)
139144
}
140-
return res
145+
return
141146
}
142147
143-
type IntHeap []int
148+
type hp struct{ sort.IntSlice }
144149
145-
func (h IntHeap) Len() int { return len(h) }
146-
func (h IntHeap) Less(i, j int) bool { return h[i] < h[j] }
147-
func (h IntHeap) Swap(i, j int) { h[i], h[j] = h[j], h[i] }
148-
func (h *IntHeap) Push(x interface{}) {
149-
*h = append(*h, x.(int))
150+
func (h hp) Less(i, j int) bool { return h.IntSlice[i] < h.IntSlice[j] }
151+
func (h *hp) Push(v interface{}) { h.IntSlice = append(h.IntSlice, v.(int)) }
152+
func (h *hp) Pop() interface{} {
153+
a := h.IntSlice
154+
v := a[len(a)-1]
155+
h.IntSlice = a[:len(a)-1]
156+
return v
150157
}
151-
func (h *IntHeap) Pop() interface{} {
152-
old := *h
153-
n := len(old)
154-
x := old[n-1]
155-
*h = old[0 : n-1]
156-
return x
158+
```
159+
160+
### **TypeScript**
161+
162+
```ts
163+
function connectSticks(sticks: number[]): number {
164+
const pq = new Heap(sticks);
165+
let ans = 0;
166+
while (pq.size() > 1) {
167+
const x = pq.pop();
168+
const y = pq.pop();
169+
ans += x + y;
170+
pq.push(x + y);
171+
}
172+
return ans;
173+
}
174+
175+
type Compare<T> = (lhs: T, rhs: T) => number;
176+
177+
class Heap<T = number> {
178+
data: Array<T | null>;
179+
lt: (i: number, j: number) => boolean;
180+
constructor();
181+
constructor(data: T[]);
182+
constructor(compare: Compare<T>);
183+
constructor(data: T[], compare: Compare<T>);
184+
constructor(data: T[] | Compare<T>, compare?: (lhs: T, rhs: T) => number);
185+
constructor(
186+
data: T[] | Compare<T> = [],
187+
compare: Compare<T> = (lhs: T, rhs: T) =>
188+
lhs < rhs ? -1 : lhs > rhs ? 1 : 0,
189+
) {
190+
if (typeof data === 'function') {
191+
compare = data;
192+
data = [];
193+
}
194+
this.data = [null, ...data];
195+
this.lt = (i, j) => compare(this.data[i]!, this.data[j]!) < 0;
196+
for (let i = this.size(); i > 0; i--) this.heapify(i);
197+
}
198+
199+
size(): number {
200+
return this.data.length - 1;
201+
}
202+
203+
push(v: T): void {
204+
this.data.push(v);
205+
let i = this.size();
206+
while (i >> 1 !== 0 && this.lt(i, i >> 1)) this.swap(i, (i >>= 1));
207+
}
208+
209+
pop(): T {
210+
this.swap(1, this.size());
211+
const top = this.data.pop();
212+
this.heapify(1);
213+
return top!;
214+
}
215+
216+
top(): T {
217+
return this.data[1]!;
218+
}
219+
heapify(i: number): void {
220+
while (true) {
221+
let min = i;
222+
const [l, r, n] = [i * 2, i * 2 + 1, this.data.length];
223+
if (l < n && this.lt(l, min)) min = l;
224+
if (r < n && this.lt(r, min)) min = r;
225+
if (min !== i) {
226+
this.swap(i, min);
227+
i = min;
228+
} else break;
229+
}
230+
}
231+
232+
clear(): void {
233+
this.data = [null];
234+
}
235+
236+
private swap(i: number, j: number): void {
237+
const d = this.data;
238+
[d[i], d[j]] = [d[j], d[i]];
239+
}
157240
}
158241
```
159242

0 commit comments

Comments
 (0)