P7606 [THUPC2021] 混乱邪恶 解题报告

P7606 [THUPC2021] 混乱邪恶 解题报告

首先,第一步小转化:

 \    /           	|  /
  \  /            	| /
——————————    ->   ------------   
  /  \             /|
 /    \           / |

这样就方便描述坐标了。

然后肉眼可见可以 dp

定义状态 \(f_{i,l,g,x,y}\space\space\space(i,l,g,x,y\in [1,100])\) 表示用到 \(i\) idea ,能否到达 \((x,y)\) 并且 \(L=l,R=r\) 。时空复杂度不对劲。第一维滚动数组滚掉。整体可以用 bitset 卡常。

然后有一个结论性的东西:引入随机化后模拟随机游走,每次挑一个方向走,走 \(n\) 次后距离远点的期望距离不超过 \(\sqrt{n}\) ,但我不会有关证明,只能贺题解。这样貌似数组最后两维开到根号级别就行了。总时间复杂度 \(O(\frac{p^4}{\omega})\) ,其他题解不是这样写的,但无所谓,\(p,n\) 同阶。

代码:

#include<bits/stdc++.h>
using namespace std;
using ll=long long;
const int maxn=100;
int n,p,a[maxn+10][maxn/4];
bitset<maxn/2>f[2][maxn+2][maxn+2][maxn/2];
#define mod(x,y) ((x-y+p)%p)
int main(){
	ios::sync_with_stdio(0),cin.tie(0);
//	freopen("P7606_7.in","r",stdin);
//	freopen("ans.out","w",stdout);
	cin>>n>>p;
	for(int i=1;i<=n;++i)
		for(int j=1;j<=12;++j)cin>>a[i][j];
	int sq=(int)sqrt(n)+2;
	random_shuffle(a+1,a+1+n);
	f[0][0][0][sq][sq]=1;
	for(int i=1;i<=n;++i){
		for(int l=0;l<p;++l){
			for(int g=0;g<p;++g){
				for(int x=0;x<=sq<<1;++x){
						f[i&1][l][g][x].reset();
						f[i&1][l][g][x]|=f[(i&1)^1][mod(l,a[i][1])][mod(g,a[i][2])][x]<<1;
						f[i&1][l][g][x]|=f[(i&1)^1][mod(l,a[i][3])][mod(g,a[i][4])][x+1];
						f[i&1][l][g][x]|=f[(i&1)^1][mod(l,a[i][5])][mod(g,a[i][6])][x+1]>>1;
						f[i&1][l][g][x]|=f[(i&1)^1][mod(l,a[i][7])][mod(g,a[i][8])][x]>>1;
						f[i&1][l][g][x]|=f[(i&1)^1][mod(l,a[i][9])][mod(g,a[i][10])][x-1];
						f[i&1][l][g][x]|=f[(i&1)^1][mod(l,a[i][11])][mod(g,a[i][12])][x-1]<<1;
				}
			}
		}
	}int l_,g_;
	cin>>l_>>g_;
	cout<<(f[n&1][l_][g_][sq][sq]?"Chaotic Evil":"Not a true problem setter");
	return 0;
}

后话:总感觉这种随机化有点不太严谨,金钩的题解提到了 \(\sqrt{n}\) 会被卡,可见这个结论要带个常数,并且“期望”步数不等于实际步数,感觉题解里的解法怪怪的,不过可以去看看官方严谨证明 如何评价2021 THUPC(清华校赛)? - 知乎 (zhihu.com),这证明难度评黑不过分吧。

posted @ 2024-08-28 08:06  余亦宸  阅读(13)  评论(1)    收藏  举报