IPO
难度:
标签:
题目描述
假设 力扣(LeetCode)即将开始 IPO 。为了以更高的价格将股票卖给风险投资公司,力扣 希望在 IPO 之前开展一些项目以增加其资本。 由于资源有限,它只能在 IPO 之前完成最多 k
个不同的项目。帮助 力扣 设计完成最多 k
个不同项目后得到最大总资本的方式。
给你 n
个项目。对于每个项目 i
,它都有一个纯利润 profits[i]
,和启动该项目需要的最小资本 capital[i]
。
最初,你的资本为 w
。当你完成一个项目时,你将获得纯利润,且利润将被添加到你的总资本中。
总而言之,从给定项目中选择 最多 k
个不同项目的列表,以 最大化最终资本 ,并输出最终可获得的最多资本。
答案保证在 32 位有符号整数范围内。
示例 1:
输入:k = 2, w = 0, profits = [1,2,3], capital = [0,1,1] 输出:4 解释: 由于你的初始资本为 0,你仅可以从 0 号项目开始。 在完成后,你将获得 1 的利润,你的总资本将变为 1。 此时你可以选择开始 1 号或 2 号项目。 由于你最多可以选择两个项目,所以你需要完成 2 号项目以获得最大的资本。 因此,输出最后最大化的资本,为 0 + 1 + 3 = 4。
示例 2:
输入:k = 3, w = 0, profits = [1,2,3], capital = [0,1,2] 输出:6
提示:
1 <= k <= 105
0 <= w <= 109
n == profits.length
n == capital.length
1 <= n <= 105
0 <= profits[i] <= 104
0 <= capital[i] <= 109
代码结果
运行时间: 70 ms, 内存: 36.9 MB
// Java Stream solution
// 思路:
// 1. 使用 Java Stream 将项目进行排序和过滤。
// 2. 使用最大堆存储当前可以完成的项目的利润。
// 3. 使用 Streams 实现堆的操作和资本的更新。
import java.util.*;
import java.util.stream.*;
class IPOStream {
public int findMaximizedCapital(int k, int w, int[] profits, int[] capital) {
// 将项目数据组合为 Pair 并排序
List<int[]> projects = IntStream.range(0, profits.length)
.mapToObj(i -> new int[]{capital[i], profits[i]})
.sorted(Comparator.comparingInt(a -> a[0]))
.collect(Collectors.toList());
PriorityQueue<Integer> maxHeap = new PriorityQueue<>(Comparator.reverseOrder());
Iterator<int[]> iterator = projects.iterator();
for (int i = 0; i < k; i++) {
while (iterator.hasNext() && iterator.next()[0] <= w) {
maxHeap.offer(iterator.next()[1]);
}
if (maxHeap.isEmpty()) break;
w += maxHeap.poll();
}
return w;
}
}
解释
方法:
This solution uses a greedy algorithm combined with a priority queue (heap) to efficiently select projects that maximize capital. Initially, it checks if the starting capital 'w' is greater than or equal to the highest capital requirement among the projects. If this is the case, it sorts the profits in descending order and picks the top 'k' to get the maximum profit immediately. Otherwise, it pairs each project with its capital and profit, sorts these pairs based on capital, and then uses a max-heap to keep track of the most profitable projects that can be started with the current capital. In each iteration (up to 'k' times), it pushes all feasible projects (based on current capital) into the heap and then selects the project with the highest profit. The profit of the selected project is added to the capital, and this process repeats until 'k' projects are completed or no further projects can be initiated.
时间复杂度:
O(n log n)
空间复杂度:
O(n)
代码细节讲解
🦆
在题解中提到,如果初始资本大于所有项目的资本要求时,将直接选择利润最高的k个项目。这种方法是否总是最优的,还是有可能因为资本的增加而错过了更高利润的项目?
▷🦆
题解使用了贪心算法结合优先队列,这种方法在所有情况下都能保证找到最大化的最终资本吗?
▷🦆
题解中提到,将项目按资本要求进行排序和利用最大堆来选择最高利润的项目。这种双结构方法是如何互补的,能否具体解释它们各自的作用和优势?
▷🦆
在实际实现时,使用了负值来模拟最大堆。这种做法有什么特别的考虑吗,为什么不直接使用最大堆实现库?
▷