考虑容斥,令$f(S)$为要求$\forall p\in S,p$可以作为起点的方案数,答案即$\sum_{S\subseteq[0,n)}(-1)^{|S|}f(S)$

关于计算$f(S)$,对于第$i$个机器人而言,$p$可以作为起点实际上即给出了$X_{i}$和$Y_{i}$每一位上的一种限制,限制共有四种(令两者分别为$x$和$y$,即$y=0,y=1,x=y$和$x\ne y$)

对每种限制预处理出第$i$个机器人以$p$为起点第$j$位上是否存在该限制,并用unsigned int存储,即可$o(n)$合并限制,进而对每一个位置分别求出满足此限制下的方案数,全部相乘即为$f(S)$

(另外需要注意如果会超出范围,仍存在全为空位的一组解)

预处理复杂度为$o(n^{2}m)$,求$f(S)$的复杂度为$o(nm)$,时间复杂度为$o(nm2^{n})$,无法通过

进一步的,预处理出子集并,再简单分类讨论即可快速求出方案数(一个unsigned int的2的位数可以将其前后的16位拆开分别处理),时间复杂度降为$o(m2^{n})$,仍无法通过

考虑优化,设第$i$个机器人有$r_{i}$个'R',那么若$r_{i}+\max_{x\in S}x\ge n$即会导致其对答案没有贡献

接下来,考虑暴力枚举$\max_{x\in S}x$并对其分类讨论:

1.若$\max_{x\in S}x<\lceil\frac{n}{2}\rceil$,直接暴力枚举$S$即可,时间复杂度为$o(m2^{\frac{n}{2}})$

2.若$\max_{x\in S}x\ge \lceil\frac{n}{2}\rceil$,那么若$r_{i}+x\ge n$其对答案也没有贡献,不需要考虑

换言之,此时即有$0\le r_{i}<x$,那么一个位置对答案是否有贡献仅取决于其之前$x$个格子的起点状态以及再之前是否存在起点(即要求相同)

由此,记录这些状态即可状压dp,通过预处理也可以做到$o((n^{2}+m)2^{\frac{n}{2}})$

综上,总复杂度为$o((n^{2}+m)2^{\frac{n}{2}})$,可以通过

  1 #include<bits/stdc++.h>
2 using namespace std;
3 #define N 35
4 #define M 1005
5 #define L (1<<16)
6 #define mod 1000000007
7 #define inv2 500000004
8 #define inv3 333333336
9 #define inv5 400000003
10 #define ll long long
11 #define ui unsigned int
12 int n,m,R,nn,ans,mi2[N],mi3[N],cnt[L],r[M];
13 char s[105];
14 ui o=1,lim[M][N][4],Lim[L][4];
15 int lowbit(int k){
16 return (k&(-k));
17 }
18 void get(int k){
19 int nn=(n+1>>1);
20 for(int i=0;i<nn;i++)memcpy(Lim[1<<i],lim[k][i],sizeof(lim[k][i]));
21 for(int S=1;S<(1<<nn);S++)
22 for(int i=0;i<4;i++)Lim[S][i]=(Lim[lowbit(S)][i]|Lim[S^lowbit(S)][i]);
23 }
24 namespace Subtask1{
25 int sum[L];
26 int count(ui k){
27 return cnt[k>>16]+cnt[k&(L-1)];
28 }
29 void calc(){
30 nn=(n+1>>1);
31 for(int S=1;S<(1<<nn);S++)sum[S]=1;
32 for(int i=1;i<=m;i++){
33 get(i);
34 for(int S=1;S<(1<<min(n-r[i],nn));S++){
35 ui p0=Lim[S][0],p1=Lim[S][1];
36 ui p2=Lim[S][2],p3=Lim[S][3];
37 ui P0=((p0&p1)|(p2&p3));
38 if (n<32)P0^=(o<<n)-1;
39 else P0^=(ui)(-1);
40 ui P1=((p0|p1)&(p2|p3)&P0);
41 sum[S]=(ll)mi2[count(P1)]*mi3[count(P0^P1)]%mod*sum[S]%mod;
42 }
43 }
44 for(int S=1;S<(1<<nn);S++)
45 if (cnt[S]&1)ans=(ans+sum[S])%mod;
46 else ans=(ans-sum[S]+mod)%mod;
47 }
48 }
49 namespace Subtask2{
50 int id[M],g[L][2],f[2][L][2];
51 bool cmp(int x,int y){
52 return r[x]<r[y];
53 }
54 void calc(){
55 for(int i=1;i<=m;i++)id[i]=i;
56 sort(id+1,id+m+1,cmp);
57 nn=(n>>1);
58 for(int S=0;S<(1<<nn);S++)g[S][0]=g[S][1]=1;
59 for(int x=n-1,k=1;x>=n-nn;x--){
60 while ((k<=m)&&(r[id[k]]+x<n)){
61 get(id[k]);
62 for(int S=0;S<(1<<nn);S++){
63 int p0=((Lim[S][0]>>nn-1)&1),p1=((Lim[S][1]>>nn-1)&1);
64 int p2=((Lim[S][2]>>nn-1)&1),p3=((Lim[S][3]>>nn-1)&1);
65 if ((p0&p1)||(p2&p3))continue;
66 if ((p0|p1)&&(p2|p3))g[S][0]=2*g[S][0]%mod;
67 else{
68 if (p0|p1|p2|p3)g[S][0]=3LL*g[S][0]%mod;
69 else g[S][0]=5LL*g[S][0]%mod;
70 }
71 p2=1;
72 if ((p0&p1)||(p2&p3))continue;
73 if ((p0|p1)&&(p2|p3))g[S][1]=2*g[S][1]%mod;
74 else g[S][1]=3LL*g[S][1]%mod;
75 }
76 k++;
77 }
78 memset(f[0],0,sizeof(f[0]));
79 f[0][0][0]=1;
80 for(int i=0;i<x;i++){
81 int ii=(i&1);
82 memset(f[ii^1],0,sizeof(f[ii^1]));
83 for(int S=0;S<(1<<nn);S++){
84 int p=(S&1),SS=(S>>1);
85 f[ii^1][SS][p]=(f[ii^1][SS][p]+(ll)g[SS][1]*f[ii][S][0])%mod;
86 f[ii^1][SS][1]=(f[ii^1][SS][1]+(ll)g[SS][1]*f[ii][S][1])%mod;
87 SS|=(1<<nn-1);
88 f[ii^1][SS][p]=(f[ii^1][SS][p]-(ll)g[SS][1]*f[ii][S][0]%mod+mod)%mod;
89 f[ii^1][SS][1]=(f[ii^1][SS][1]-(ll)g[SS][1]*f[ii][S][1]%mod+mod)%mod;
90 }
91 }
92 for(int S=0;S<(1<<nn);S++){
93 int p=(S&1),SS=((S>>1)|(1<<nn-1)),s=f[x&1][S][0];
94 for(int j=x;j<n;j++){
95 s=(ll)s*g[SS][p]%mod;
96 p|=(SS&1),SS>>=1;
97 }
98 ans=(ans+s)%mod;
99 SS=((S>>1)|(1<<nn-1)),s=f[x&1][S][1];
100 for(int j=x;j<n;j++){
101 s=(ll)s*g[SS][1]%mod;
102 SS>>=1;
103 }
104 ans=(ans+s)%mod;
105 }
106 }
107 }
108 }
109 int main(){
110 mi2[0]=mi3[0]=1;
111 for(int i=1;i<N;i++){
112 mi2[i]=2*mi2[i-1]%mod;
113 mi3[i]=3LL*mi3[i-1]%mod;
114 }
115 for(int i=1;i<L;i++)cnt[i]=cnt[i^lowbit(i)]+1;
116 scanf("%d%d",&n,&m);
117 for(int i=1;i<=m;i++){
118 scanf("%s",s);
119 for(int j=0;s[j];j++)
120 if (s[j]=='R')r[i]++;
121 for(int j=0;j<n-r[i];j++){
122 for(int k=0;k<j;k++)lim[i][j][2]|=(o<<k);
123 for(int k=j+r[i]+1;k<n;k++)lim[i][j][2]|=(o<<k);
124 int pos=j,lst=2;
125 for(int k=0;s[k];k++){
126 if (s[k]=='R'){
127 lim[i][j][lst]|=(o<<pos);
128 pos++,lst=2;
129 }
130 else{
131 if (s[k]=='*')lst^=1;
132 else lst=s[k]-'0';
133 }
134 }
135 lim[i][j][lst]|=(o<<pos);
136 }
137 }
138 Subtask1::calc();
139 Subtask2::calc();
140 printf("%d\n",ans);
141 return 0;
142 }

[luogu7740]机器人游戏的更多相关文章

  1. Solution -「NOI 2021」「洛谷 P7740」机器人游戏

    \(\mathcal{Description}\)   Link.   自己去读题面叭~ \(\mathcal{Solution}\)   首先,参悟[样例解释 #2].一种暴力的思路即为钦定集合 \ ...

  2. 玩家福音:10款最佳Linux免费游戏

    “我能在Linux平台上游戏吗?”这类疑问正困扰游戏玩家,那么答案就是“快去Linux平台吧!”.开源组织一直以来坚持不懈为Linux操作系统开发不同类型的游戏,在Linux平台下的游戏完全不亚于其他 ...

  3. 开源玩家福利:十大Linux免费游戏

    假如当你考虑从Windows平台迁移至Linux平台时,“我能在Linux平台上游戏吗?”这类疑问正困扰着你,那么对此这有一个答案就是“快去Linux平台吧!”.感谢开源组织一直以来坚持不懈为Linu ...

  4. Unity3d入门 - 关于unity工具的熟悉

    上周由于工作内容较多,花在unity上学习的时间不多,但总归还是学习了一些东西,内容如下: .1 根据相关的教程在mac上安装了unity. .2 学习了unity的主要的工具分布和对应工具的相关的功 ...

  5. Android 7.0真实上手体验

    Android 7.0真实上手体验 Android 7.0的首个开发者预览版发布了,支持的设备只有Nexus6.Nexus 5X.Nexus 6P.Nexus 9.Nexus Player.Pixel ...

  6. 2021NOI同步赛

    \(NOI\) 网上同步赛 明白了身为菜鸡的自己和普通人的差距 DAY1 \(T1\) 轻重边 [题目描述] 小 W 有一棵 \(n\) 个结点的树,树上的每一条边可能是轻边或者重边.接下来你需要对树 ...

  7. (NO.00003)iOS游戏简单的机器人投射游戏成形记(十八)

    在游戏中制作手臂瞄准线,也就是所谓的辅助延长线.玩台球游戏的童鞋应该可以了解. 按道理来说,延长线是一个物理实体,遇到物理刚体应该会发生反弹行为,这个符合实际游戏逻辑. 但是这里为了简单,只是做一条& ...

  8. (NO.00003)iOS游戏简单的机器人投射游戏成形记(九)

    现在按住手臂可以非常自然和舒服的旋转了,丝般顺滑:移动停止,旋转立即停止,没有什么惯性影响了. 以上一共介绍了2中旋转方式,到底采用哪种方式呢?其实看实际游戏的需求和个人的喜好了.本猫在Level中添 ...

  9. (NO.00003)iOS游戏简单的机器人投射游戏成形记(三)

    接下来我们建立机器人对象. 在Sprites文件夹中新建Robot.ccb文件,类型为Node. 打开SpriteBuilder的Tileless View将机器人身体和手臂拖入根节点,调整好相对的位 ...

随机推荐

  1. CentOS7下Hadoop伪分布式环境搭建

    CentOS7下Hadoop伪分布式环境搭建 前期准备 1.配置hostname(可选,了解) 在CentOS中,有三种定义的主机名:静态的(static),瞬态的(transient),和灵活的(p ...

  2. SphereEx 获数百万美元天使融资,接力 ShardingSphere 开启 Database Plus 新篇章

    5月14日,数据前沿技术领域初创公司 SphereEx 获得来自红杉中国种子基金.初心资本的数百万美元天使轮融资. SphereEx是一家致力于构建新型分布式数据基础设施的公司,秉承开源.共享.生态. ...

  3. java笔记(一直更新)

    .equals()调用时,最好把equals前面放常量或者是确定有的,如果是前面是null,则会报空指针错误 也可以在调用前判断是否为null

  4. C#开发BIMFACE系列50 Web网页中使用jQuery加载模型与图纸

    BIMFACE二次开发系列目录     [已更新最新开发文章,点击查看详细] 在前一篇博客<C#开发BIMFACE系列49 Web网页集成BIMFACE应用的技术方案>中介绍了目前市场主流 ...

  5. GAN实战笔记——第二章自编码器生成模型入门

    自编码器生成模型入门 之所以讲解本章内容,原因有三. 生成模型对大多数人来说是一个全新的领域.大多数人一开始接触到的往往都是机器学习中的分类任务--也许因为它们更为直观:而生成模型试图生成看起来很逼真 ...

  6. 宙斯盾 DDoS 防护系统“降本增效”的云原生实践

    作者 tomdu,腾讯云高级工程师,主要负责宙斯盾安全防护系统管控中心架构设计和后台开发工作. 导语 宙斯盾 DDoS 防护系统作为公司级网络安全产品,为各类业务提供专业可靠的 DDoS/CC 攻击防 ...

  7. 第四代富士X100F操作学习

    前言 本文为自己通过B站的UP主[阿布垃机手册]整理.原视频地址:[阿布垃机手册][布瞎BB]富士 X100F 相机外部按键 拍人像自己的设置 [X100F相机光圈大小支持F2到F16+Auto]光圈 ...

  8. 【UE4】读写 Texture 数据

    创建texture 方式一 void AActor_Assignment2::TextureFromImage_Internal( const TArray<FColor>& Sr ...

  9. 【UE4 C++ 基础知识】<12> 多线程——FRunnable

    概述 UE4里,提供的多线程的方法: 继承 FRunnable 接口创建单个线程 创建 AsyncTask 调用线程池里面空闲的线程 通过 TaskGraph 系统来异步完成一些自定义任务 支持原生的 ...

  10. webpack基础以及webpack中babel的配置

    webpack 安装 npm 初始化,控制台输入 npm init -y webpack 安装 npm i webpack webpack-cli -D 新建 webpack.config.js co ...