题目
- 链接:D. The Strongest Build
- 题意:给定n<=10组数,每组数的数量为ci<=2e5,所有ci之和也<=2e5。每组数从前到后从小到大。有m个组合不能选择,求组合大小最大的能选择的组合。
- 组合大小:下标对应的值的和。
- 题解:
- 首先应该知道是BFS,
- 然后就是STL的问题了——vector可以自己比较大小 & struct不用都重构一下 & 优先队列没那么难。
- 代码:
#include <bits/stdc++.h>
using namespace std;
const int N = 10 + 5;
int n, m, c[N], x;
vector<int> g[N], ans, v;
map<vector<int>, int> mp, mp1;
struct node {
int sum;
vector<int> v;
bool operator<(const node &b) const {
if (sum == b.sum) return v < b.v;
return sum < b.sum;
}
};
void bfs() {
priority_queue<node> q;
int sum = 0;
ans.clear();
for (int i = 1; i <= n; i++) {
sum += g[i][c[i]];
ans.push_back(c[i]);
}
q.push({sum, ans});
mp1[ans] = 1;
while (!q.empty()) {
node now = q.top();
q.pop();
ans = now.v, sum = now.sum;
if (!mp[ans]) break;
for (int i = 1; i <= n; i++) {
if (ans[i - 1] > 1) {
sum = sum - g[i][ans[i - 1]] + g[i][ans[i - 1] - 1];
ans[i - 1]--;
if (!mp1[ans]) {
q.push({sum, ans});
mp1[ans] = 1;
}
ans[i - 1]++;
sum = sum + g[i][ans[i - 1]] - g[i][ans[i - 1] - 1];
}
}
}
}
signed main() {
scanf("%d", &n);
for (int i = 1; i <= n; i++) {
scanf("%d", &c[i]);
g[i].push_back(0);
for (int j = 1; j <= c[i]; j++) {
scanf("%d", &x);
g[i].push_back(x);
}
}
scanf("%d", &m);
for (int i = 1; i <= m; i++) {
v.clear();
for (int j = 1; j <= n; j++) {
scanf("%d", &x);
v.push_back(x);
}
mp[v] = 1;
}
bfs();
for (int i = 1; i <= n; i++) cout << ans[i - 1] << " ";
return 0;
}