大致看了一眼题解,思路都是差不多的。所以不另开题解
但是如果你定义f[i][p]表示为搜索树第n−i层(全局为搜索数第0层,叶子为第n+1层),然后p的前n−i位表示这个节点在所在层的编号,后i位表示其叶子受到的交换情况。
加上一个滚动数组。
那么
cin>>n,p2n=(1<<n);
for(int i=0; i<p2n; i++)
cin>>node[0][i].sum
,node[0][i].lans=node[0][i].rans=node[0][i].ans
=std::max(0ll,node[0][i].sum);
for(int i=1; i<=n; i++)
for(int p=0; p<p2n; p++)
node[(i&1)][p]=node[((i&1)^1)][p]+node[((i&1)^1)][p^(1<<(i-1))];
int t=0,q;
cin>>q;
for(int i=1,k; i<=q; i++)
{
cin>>k;
t=(t^(1<<k));
cout<<node[n&1][t].ans<<'\n';
}
他的核心代码就显得特别美丽:
for(int i=1; i<=n; i++)
for(int p=0; p<p2n; p++)
node[(i&1)][p]=node[((i&1)^1)][p]+node[((i&1)^1)][p^(1<<(i-1))];