NKOJ P3802 不死【狀態壓縮】【二分答案】
阿新 • • 發佈:2018-12-11
二分答案即可,狀壓是比較普通的狀態:
#include <cmath> #include <cstdio> #include <cstring> #include <iostream> #include <algorithm> #define ll long long #define rep(i,x,y) for(ll i=(x);i<=(y);i++) #define repd(i,x,y) for(ll i=(x);i>=(y);i--) using namespace std; const ll N=1e5+5; const ll Inf=1e18; ll f[N][1<<6]; ll n,t=63,st,cla[N],sle[N],uns[N]; ll ans; inline ll read() { ll x=0;char ch=getchar();bool f=0; while(ch>'9'||ch<'0'){if(ch=='-')f=1;ch=getchar();} while(ch>='0'&&ch<='9'){x=(x<<1)+(x<<3)+ch-'0';ch=getchar();} return f?-x:x; } bool check(ll x) { rep(i,0,n) rep(j,0,t) f[i][j]=Inf;f[0][0]=st; rep(i,1,n) rep(j,0,t) { if(cla[i]==7) { if(f[i-1][j]<=x) f[i][j]=f[i-1][j]-sle[i]; } else { ll k=1<<(cla[i]-1); if(j&k) { if(f[i-1][j^k]<=x) f[i][j]=f[i-1][j^k]-sle[i]; } else { if(f[i-1][j]<=x) f[i][j]=min(f[i][j],f[i-1][j]+uns[i]); if(f[i-1][j^k]<=x) f[i][j]=min(f[i][j],f[i-1][j^k]+uns[i]); } } } rep(i,0,t) if(f[n][i]<=x) return true; return false; } int main() { n=read(); rep(i,1,n) cla[i]=read(); rep(i,1,n) sle[i]=read(); rep(i,1,n) uns[i]=read();st=read(); ll l=st,r=Inf; while(l<=r) { ll mid=l+r>>1; if(check(mid)) r=mid-1; else l=mid+1; } printf("%lld",l); return 0; }