题解 | #疫苗小孩#

疫苗小孩

https://ac.nowcoder.com/acm/contest/23480/A

观察到序列长度<=20,那么显然我们可以用状态压缩去枚举我们的礼遇用在那一场战斗, 1<<20=1024*1024复杂度可以接受。

即我们用一段01串去模拟使用礼遇和不使用的场景。

当第j位上为1的时候则我们可以在4个数中取max,即使用礼遇,否则只能在两个数中取最大值。

当然,我们的01串中1的数量不可以大于k

这样我们就能得到我们的得分序列,然后在贪心的从大到小排序去看我们能否符合最小得分即可

举个状态压缩的例子当我们的比赛场次为3的时候,我们的01串可以是000, 001, 010,....,111

那么他们的十进制分别是012,...,7。而(1<<3)-1恰好就是7

#include <bits/stdc++.h>

using namespace std;

typedef long long ll;
typedef pair<int, int> pii;

const int N = 2e6 + 10;
const int mod = 1e9 + 7;

int n, k, s;
int ans;
struct node
{
	int a, b, c, d;
}g[30];

int main()
{
	cin >> n >> k >> s;
	vector<int> a(n);

	for(int i = 0; i < n; i ++) {
		cin >> a[i];
	}
	for(int i = 0; i < n; i ++) {
		int a, b, c, d;
		cin >> a >> b >> c >> d;
		g[i] = {a, b, c, d};
	}

	for(int i = 0; i < (1 << n); i ++) {
		vector<int> t;
		for(int j = 0; j < n; j ++) {
			if(i >> j & 1) {
				t.emplace_back(j);
			}
		}

		if(t.size() > k) {
			continue;
		}

		vector<int> res;
		int l = 0;
		for(int j = 0; j < n; j ++) {
			if(l < t.size() && t[l] == j) {
				res.emplace_back(max({g[j].a, g[j].b, g[j].c, g[j].d}));
				l ++;
			} else {
				res.emplace_back(max(g[j].a, g[j].b));
			}
		}

		sort(res.begin(), res.end(), greater<int>());
		int cnt = 0, all = s;

		for(int j = 0; j < res.size(); j ++) {
			all += res[j];
			if(all >= a[j]) {
				cnt ++;
			}
		}
		ans = max(ans, cnt);
	}

	cout << ans;
	
	return 0;
}

百色疫情加油QAQQ

全部评论

相关推荐

刘湘_passion:出国旅游?那就小心你的腰子咯
点赞 评论 收藏
分享
评论
12
收藏
分享

创作者周榜

更多
牛客网
牛客企业服务