1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90
|
#include<iostream> #include<cstdio> #include<cmath> using namespace std; long long read() { long long x=0,f=1; char c=getchar(); while(!isdigit(c)){if(c=='-') f=-1;c=getchar();} while(isdigit(c)){x=x*10+c-'0';c=getchar();} return x*f; } const int N=2100; const long long inf=0x3f3f3f3f3f3f3f3fll; int n,m,a[N],c[N],w[N][N]; long long F[N][N],depth[N],fa[N][21]; void dfs(int now) { for(int i=1;i<=20;i++) fa[now][i]=fa[fa[now][i-1]][i-1]; if(now<(1<<n)) { fa[now*2][0]=now,depth[now*2]=depth[now]+1,dfs(now*2); fa[now*2+1][0]=now,depth[now*2+1]=depth[now]+1,dfs(now*2+1); } } int LCA(int x,int y) { if(depth[y]>depth[x]) swap(x,y); for(int i=20;i>=0;i--) if(depth[x]-(1<<i)>=depth[y]) x=fa[x][i]; if(x==y) return x; for(int i=20;i>=0;i--) if(fa[x][i]!=fa[y][i]) x=fa[x][i],y=fa[y][i]; return fa[x][0]; } long long f[N][N*2]; long long dfs2(int now,int K) { if(f[now][K]!=0) return f[now][K]; int c_now=0,cnt_B=K/(1<<depth[now]),cnt_A=(1<<(n-depth[now]))-cnt_B; if(cnt_B<0 or cnt_A<0) return f[now][K]=inf; if(cnt_B>cnt_A) c_now=1; if(now>=(1<<n)) { int tmp=K%(1<<depth[now]),t_now=now/2; for(;t_now>0;t_now/=2,tmp/=2) f[now][K]+=(c_now!=(tmp%2))*F[now][t_now]; f[now][K]+=c[now]*(a[now]!=c_now); return f[now][K]; } long long t_ans=inf; for(int i=0;i<=cnt_B;i++) { long long L=dfs2(now*2,((K%(1<<depth[now]))<<1)+c_now+i*(1<<depth[now*2])); long long R=dfs2(now*2+1,((K%(1<<depth[now]))<<1)+c_now+(cnt_B-i)*(1<<depth[now*2+1])); t_ans=min(t_ans,L+R); } return f[now][K]=t_ans; } int main() { n=read(); m=(1<<(n+1))-1; for(int i=(1<<n);i<=m;i++) a[i]=read(); for(int i=(1<<n);i<=m;i++) c[i]=read(); for(int i=(1<<n);i<=m;i++) for(int j=i+1;j<=m;j++) w[i][j]=w[j][i]=read();
dfs(1); for(int i=(1<<n);i<=m;i++) for(int j=i+1;j<=m;j++) F[i][LCA(i,j)]+=w[i][j], F[j][LCA(i,j)]+=w[i][j];
long long ans=inf; for(int i=0;i<=(1<<n);i++) ans=min(ans,dfs2(1,i));
printf("%lld",ans); return 0; }
|