P8903 [USACO22DEC] Bribing Friends G

暴力 dp 是简单的。

实际上的消费情况按 \(X_i\) 从小到大排序,为存在中转点 \(i\)\([1,i)\) 均用甜筒,\((i,n]\) 均用哞尼,\(i\) 用若干甜筒 + 若干哞尼。

假设在 \((i,n]\) 用了 \(x\) 个甜筒换了 \(c\) 哞尼而 \([1,i)\) 用了 \(y\) 哞尼,那么这 \(x\) 个甜筒拿到 \([1,i)\) 换到的哞尼数 \(c'\) 必定不小于 \(c\),再拿换到的哞尼换出那 \(y\) 哞尼扔到后面,这样显然不劣。

于是只需要求出 \(f_{i,j},g_{i,j}\) 分别表示前缀 \(i\)\(j\) 甜筒 / 后缀 \(i\)\(j\) 哞尼能得到的最大欢迎度。

统计答案时枚举中转点 \(i\) 以及 \(i\) 用了多少哞尼直接合并对应的 \(f,g\) 状态即可。

#include<bits/stdc++.h>
#define fin(x) freopen(#x".in","r",stdin)
#define fout(x) freopen(#x".out","w",stdout)
#define fr(x) fin(x),fout(x);
#define Fr(x,y) fin(x),fout(y)
#define INPUT(_1,_2,FILE,...) FILE
#define IO(...) INPUT(__VA_ARGS__,Fr,fr)(__VA_ARGS__)
using namespace std;
#define mp make_pair
#define pii pair<int,int>
#define fi first
#define se second
#define pb push_back
#define cfast ios::sync_with_stdio(false);cin.tie(0),cout.tie(0)
#define ll long long
#define ull unsigned long long
#define intz(x,y) memset((x),(y),sizeof((x)))
char *p1,*p2,buf[100000];
#define nc() (p1==p2 && (p2=(p1=buf)+fread(buf,1,100000,stdin),p1==p2)?EOF:*p1++)
#define tup(x) array<int,(x)>
inline ll read(){
    ll x=0,f=1;char ch=nc();
    while(ch<48||ch>57){if(ch=='-')f=-1;ch=nc();}
    while(ch>=48&&ch<=57)x=x*10+ch-48,ch=nc();
   	return x*f;
}
//void write(int x){cout<<x<<' ';}
//void write(pii x){cout<<"P("<<x.fi<<','<<x.se<<")\n";}
//void write(vector<auto>x){for(auto i:x)write(i);cout<<'\n';}
//void write(auto *a,int l,int r){for(int i=l;i<=r;i++)write(a[i]);cout<<'\n';}
inline ll lowbit(ll x){return x&-x;}
inline int pcount(ll x){
	for(int i=0,res=0;;res+=(x>>i)&1,i++)
		if(i>60)return res;
}

//struct mt{
//	ll v;
//	mt(){v=0;}
//	mt(int x){this->v=x;}
//	inline mt operator+(mt x){return {(v+x.v)%mod};}
//	inline mt operator-(mt x){return {(v+mod-x.v)%mod};}
//	inline mt operator*(mt x){return {1ll*v*x.v%mod};}
//};
//mt qp(mt x,int y){mt res(1);for(;y;x=x*x,y>>=1)if(y&1)res=res*x;return res;}
const int N=2005;
struct node{int x,y,z;}a[N];
int f[N][N],g[N][N];
inline void UesugiErii(){
	int n,A,B;cin>>n>>A>>B;
	for(int i=1;i<=n;i++)
		cin>>a[i].x>>a[i].y>>a[i].z;
	sort(a+1,a+1+n,[](node x,node y){return x.z<y.z;});
	for(int i=1;i<=n;i++)
		for(int j=0;j<=B;j++){
			f[i][j]=f[i-1][j];
			if(j>=a[i].y*a[i].z)
				f[i][j]=max(f[i][j],f[i-1][j-a[i].y*a[i].z]+a[i].x);
		}
	for(int i=n;i;i--)
		for(int j=0;j<=A;j++){
			g[i][j]=g[i+1][j];
			if(j>=a[i].y)
				g[i][j]=max(g[i][j],g[i+1][j-a[i].y]+a[i].x);
		}
	int ans=0;
	for(int i=1;i<=n;i++)
		for(int j=0;j<=min(a[i].y,A);j++)
			if((a[i].y-j)*a[i].z<=B)
				ans=max(ans,f[i-1][B-(a[i].y-j)*a[i].z]+a[i].x+g[i+1][A-j]);
	cout<<ans;
}
signed main(){
	//IO();//cfast;
	int _=1;//cin>>_;
	for(;_;_--)UesugiErii();
	return 0;
}
posted @ 2025-11-18 18:56  Uesugi1  阅读(4)  评论(0)    收藏  举报