BZOJ4676: Xor-Mul棋盘

BZOJ4676: Xor-Mul棋盘

https://lydsy.com/JudgeOnline/problem.php?id=4675

分析:

  • 就是个简单的拆位DP,不要想得太复杂
  • 位与位之间互不影响,对每一位分别求然后加和
  • (f[i][j])表示前(i)列,第(i)列的状态是(j)的答案。

代码:

#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
typedef long long ll;
#define N 10
#define M 10050
int n,m;
int a[N][M],b[N][M],c1[N][M],c2[N][M],c3[M];
ll f[M][40],cal[M][40],cal2[M][40];
char buf[100000],*p1,*p2;
#define nc() (p1==p2&&(p2=(p1=buf)+fread(buf,1,100000,stdin),p1==p2)?EOF:*p1++)
int rd() {
	int x=0; char s=nc();
	while(s<'0') s=nc();
	while(s>='0') x=(((x<<2)+x)<<1)+s-'0',s=nc();
	return x;
}
template <typename T> void chkmin(T &x,T y) {x=x<y?x:y;}
ll calc(int p,int c,int s) {
	int i;
	ll re=0;
	if(((s>>(n-1))&1) != (s&1)) {
		re+=ll(1<<p)*c3[c];
	}
	for(i=1;i<=n;i++) {
		if( ((s>>(i-1))&1) != ((a[i][c]>>p)&1)) {
			re+=ll(1<<p)*b[i][c];
		}
		if(i!=n) if( ((s>>(i-1))&1) != ((s>>i)&1)) {
			re+=ll(1<<p)*c2[i][c];
		}
	}
	return re;
}
ll calc2(int p,int c,int s) {
	int i;
	ll re=0;
	for(i=1;i<=n;i++) {
		if(s&(1<<(i-1))) {
			re+=ll(1<<p)*c1[i][c];
		}
	}
	return re;
}
int main() {
	scanf("%d%d",&n,&m);
	int i,j,k,p,l=0,mx=0;
	for(i=1;i<=n;i++) {
		for(j=1;j<=m;j++) {
			a[i][j]=rd();
			mx=max(mx,a[i][j]);
		}
	}
	for(i=1;i<=n;i++) {
		for(j=1;j<=m;j++) {
			b[i][j]=rd();
		}
	}
	for(i=1;i<=n;i++) {
		for(j=1;j<m;j++) {
			c1[i][j]=rd();
		}
	}
	for(i=1;i<n;i++) {
		for(j=1;j<=m;j++) {
			c2[i][j]=rd();
		}
	}
	
	for(i=1;i<=m;i++) c3[i]=rd();
	int mask=(1<<n)-1;

	ll ans=0;
	for(p=0;(1<<p)<=mx;p++) {
		for(i=1;i<=m;i++) {
			for(j=0;j<=mask;j++) {
				cal[i][j]=calc(p,i,j);
				if(i!=m) cal2[i][j]=calc2(p,i,j);
			}
		}
		memset(f,0x3f,sizeof(f));
		for(i=0;i<=mask;i++) {
			f[1][i]=cal[1][i];
		}
		for(i=1;i<m;i++) {
			for(j=0;j<=mask;j++) if(f[i][j]<1ll<<60) {
				ll tmp=f[i][j];
				for(k=0;k<=mask;k++) {
					chkmin(f[i+1][k],tmp+cal[i+1][k]+cal2[i][j^k]);
				}
			}
		}
		ll mn=1ll<<60;
		for(i=0;i<=mask;i++) chkmin(mn,f[m][i]);
		ans+=mn;
	}
	printf("%lld
",ans);
}


原文地址:https://www.cnblogs.com/suika/p/10051660.html