CF1458E Nim Shortcuts
I.CF1458E Nim Shortcuts
我们考虑把一对石子堆 映射到笛卡尔平面上的一个点 。
先考虑没有捷径时的方案。很明显,这是简单的NIM游戏,当且仅当直线 上的状态是先手必败态。但是,我们有必要搞清楚该结论的由来:
如果对于一个位置 ,不存在任何一个可以由它一步走到的必败态,则它就是必败态;否则就是必胜态。在NIM游戏中,位置 可以走到所有的 和 ,其中 。
首先,位置 肯定是必败态;于是由上文结论,所有其它 和 的位置都是必胜态;,因为不存在任何一个与其同行列的必败态,故也是必败态,然后所有其它 和 的态都是必胜态……
我们仍然考虑上述分析,只不过现在有了“捷径”。
考虑当前已经分析到了位置 。显然,如果不存在任何一个与它同行列的“捷径”,则有无捷径并无影响,直接把 看作必败态,然后继续去分析 。
否则,存在一个与它同行列的“捷径”。这里先分析有同列的情况(即有相同的 值)。设该捷径为 。
明显,若 ,捷径 并不可能从位置 走到,也就无从对其产生影响了,于是就和上文一样处理即可。
否则,即 ,此时 可以走到 (当然,二者可能重合——但是此时因为 会在行上和列上同时被看作可以走到的位置,所以不会产生影响),因为 是必败态,所以此时 就成了必胜态。因为在 这一行上还没有必败态,但是 这一列上已经有必败态了,所以把 看作必胜态,然后分析 。
存在一个同行(相同的 )的捷径的情况也类似,此时接下来要分析的是 。当然,两个也可能同时发生——此时应考虑 。
初始直接开始分析位置 。
明显,我们只需要考虑关键的行和列即可,剩下的位置直接按照一条斜率为 的线段进行处理即可。询问的时候先判断其本身是否是一个“捷径”,然后再判断其是否在一条上述线段上。使用 set
之类加以维护,时间复杂度 。
代码:
#include<bits/stdc++.h>
using namespace std;
int n,m,x,y;
map<pair<int,int>,bool>mp;
map<int,int>X,Y;
set<tuple<int,int,int> >s;
int main(){
scanf("%d%d",&n,&m);
for(int i=1;i<=n;i++){
scanf("%d%d",&x,&y),mp[make_pair(x,y)]=true;
if(X.find(x)==X.end())X[x]=y;else X[x]=min(X[x],y);
if(Y.find(y)==Y.end())Y[y]=x;else Y[y]=min(Y[y],x);
}
x=y=0;
for(auto i=X.begin(),j=Y.begin();i!=X.end()||j!=Y.end();){
while(i!=X.end()&&i->first<x)i++;
while(j!=Y.end()&&j->first<y)j++;
int xx=0x3f3f3f3f,yy=0x3f3f3f3f;
if(i!=X.end())xx=i->first;
if(j!=Y.end())yy=j->first;
int mn=min(xx-x,yy-y);
bool xxx=false,yyy=false;
if(x+mn==xx&&i->second<=y+mn)xxx=true;
if(y+mn==yy&&j->second<=x+mn)yyy=true;
// printf("(%d,%d)->(%d,%d):%d %d|%d,%d\n",x,y,x+mn,y+mn,xxx,yyy,xx,yy);
if(mn+1-max(xxx,yyy))s.insert(make_tuple(x+mn-max(xxx,yyy),x,y));
if(!max(xxx,yyy))xxx=yyy=true;
x+=mn+xxx,y+=mn+yyy;
}
s.insert(make_tuple(0x3f3f3f3f,x,y));
// for(auto i:s)printf("(%d,%d)(%d,%d)\n",get<1>(i),get<2>(i),get<0>(i),get<2>(i)+get<0>(i)-get<1>(i));
for(int i=1;i<=m;i++){
scanf("%d%d",&x,&y);
if(mp.find(make_pair(x,y))!=mp.end()){puts("LOSE");continue;}
auto tmp=s.lower_bound(make_tuple(x,0,0));
if(tmp==s.end()||get<1>(*tmp)>x){puts("WIN");continue;}
puts(get<2>(*tmp)+x-get<1>(*tmp)==y?"LOSE":"WIN");
}
return 0;
}
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列1:轻松3步本地部署deepseek,普通电脑可用
· 按钮权限的设计及实现
· 【杂谈】分布式事务——高大上的无用知识?