1. 题目来源
题单:
- 待补充
2. 题目解析
思路一: 排序
- 第一种排序的想法没有想到。
- 一定可以完全按照降序的方式取完所有数据。即便两次取在了同一行,那也说明第二次取的该行数据也是比其他的末尾数据还要小的。也是合法写法。
- 理解这个后,直接将二维数组一维化,然后排序就行了。
思路二: 最小堆
- 这个就很容易理解了,类似与多路归并一样,拿最小堆维护当前的最小值即可。
- 也是直接采用这个方法写的。
- 时间复杂度: O ( n log ( n ) ) O(n \log(n)) O(nlog(n))
- 空间复杂度: O ( n ) O(n) O(n)
方法一:排序
class Solution {
public:
long long maxSpending(vector<vector<int>>& values) {
typedef long long LL;
LL res = 0;
vector<int> f;
for (auto vv : values) for (auto v : vv) f.push_back(v);
sort(f.begin(), f.end());
for (int i = 1; i <= f.size(); i ++ ) res += 1ll * i * f[i - 1];
return res;
}
};
方法二:最小堆
class Solution {
public:
long long maxSpending(vector<vector<int>>& values) {
typedef long long LL;
typedef pair<int, int> PII;
#define x first
#define y second
priority_queue<PII, vector<PII>, greater<PII>> q;
int n = values.size(), m = values[0].size();
vector<int> idx(n, m);
for (int i = 0; i < n; i ++ ) q.push({values[i][m - 1], i});
LL res = 0;
for (int i = 1; i <= n * m; i ++ ) {
auto t = q.top(); q.pop();
res += 1ll * i * t.x;
if (idx[t.y] > 1) {
idx[t.y] -- ;
q.push({values[t.y][idx[t.y] - 1], t.y});
}
}
return res;
}
};