fzu1977
题解:
和前两题差不多
只不过变成了有些一定走,有些不一定
代码:
#include<cstdio>
#include<cmath>
#include<algorithm>
#include<cstring>
using namespace std;
typedef long long ll;
const int HASH=;
const int STATE=;
int N,M,code[],maze[][],ch[],isend;
struct HASHMAP
{
int head[HASH],next[STATE],size;
ll state[STATE],f[STATE];
void init()
{
size=;
memset(head,-,sizeof(head));
}
void push(ll st,ll ans)
{
int h=st%HASH;
for (int i=head[h];i!=-;i=next[i])
if (state[i]==st)
{
f[i]+=ans;
return;
}
state[size]=st;
f[size]=ans;
next[size]=head[h];
head[h]=size++;
}
}hm[];
void decode(int *code,int m,ll st)
{
for (int i=m;i>=;i--)
{
code[i]=st&;
st>>=;
}
isend=st&;
}
ll encode(int *code,int m)
{
int cnt=;
memset(ch,-,sizeof(ch));
ch[]=;
ll st=isend;
for (int i=;i<=m;i++)
{
if (ch[code[i]]==-)ch[code[i]]=cnt++;
code[i]=ch[code[i]];
st<<=;
st|=code[i];
}
return st;
}
void shift(int *code,int m)
{
for (int i=m;i>;i--)code[i]=code[i-];
code[]=;
} void dpblank(int i,int j,int cur)
{
int left,up;
for (int k=;k<hm[cur].size;k++)
{
decode(code,M,hm[cur].state[k]);
left=code[j-];
up=code[j];
if (isend)
{
if (left||up||maze[i][j]==)continue;
code[j-]=code[j]=;
if (j==M)shift(code,M);
hm[cur^].push(encode(code,M),hm[cur].f[k]);
continue;
}
if (left&&up)
{
if (left==up)
{
code[j-]=code[j]=;
isend=;
if(j==M)shift(code,M);
hm[cur^].push(encode(code,M),hm[cur].f[k]);
}
else
{
code[j-]=code[j]=;
for (int t=;t<=M;t++)
if (code[t]==up)code[t]=left;
if (j==M)shift(code,M);
hm[cur^].push(encode(code,M),hm[cur].f[k]);
}
}
else if ((left&&(!up))||((!left)&&up))
{
int t;
if (left)t=left;
else t=up;
if (maze[i][j+])
{
code[j-]=;
code[j]=t;
hm[cur^].push(encode(code,M),hm[cur].f[k]);
}
if (maze[i+][j])
{
code[j-]=t;
code[j]=;
if (j==M)shift(code,M);
hm[cur^].push(encode(code,M),hm[cur].f[k]);
}
}
else
{
if (maze[i][j+]&&maze[i+][j])
{
code[j-]=code[j]=;
hm[cur^].push(encode(code,M),hm[cur].f[k]);
}
if (maze[i][j]==)
{
code[j-]=code[j]=;
if (j==M)shift(code,M);
hm[cur^].push(encode(code,M),hm[cur].f[k]);
}
}
}
}
void dpblock(int i,int j,int cur)
{
for (int k=;k<hm[cur].size;k++)
{
decode(code,M,hm[cur].state[k]);
code[j-]=code[j]=;
if (j==M)shift(code,M);
hm[cur^].push(encode(code,M),hm[cur].f[k]);
}
}
char str[];
void init()
{
scanf("%d%d",&N,&M);
memset(maze,,sizeof(maze));
for (int i=;i<=N;i++)
{
scanf("%s",&str);
for (int j=;j<=M;j++)
{
if (str[j-]=='*')maze[i][j]=;
else if (str[j-]=='O')maze[i][j]=;
}
}
}
void solve()
{
int cur=;
hm[cur].init();
hm[cur].push(,);
for (int i=;i<=N;i++)
for (int j=;j<=M;j++)
{
hm[cur^].init();
if(maze[i][j])dpblank(i,j,cur);
else dpblock(i,j,cur);
cur^=;
}
ll ans=;
for (int i=;i<hm[cur].size;i++)ans+=hm[cur].f[i];
printf("%I64d\n",ans);
}
int main()
{
int T,iCase=;
scanf("%d",&T);
while (T--)
{
iCase++;
printf("Case %d: ",iCase);
init();
solve();
}
return ;
}
fzu1977的更多相关文章
- FZU1977 Pandora adventure —— 插头DP
题目链接:https://vjudge.net/problem/FZU-1977 Problem 1977 Pandora adventure Accept: 597 Submit: 2199 ...
- [FZU1977] Pandora adventure
来学插头DP了= = GDKOI前觉得不会考数位DP,GDOI前觉得插头DP用不上.. 结果令人伤感>_< 这题并不用增加状态.. 只要在形成环的时候,让形成环的位置在最后一个必走点之后, ...
- 初探插头dp
开学那个月学了点新东西,不知道还记不记得了,mark一下 感觉cdq的论文讲的很详细 题主要跟着kuangbin巨做了几道基础的 http://www.cnblogs.com/kuangbin/arc ...
随机推荐
- AtCoder Regular Contest 100 Equal Cut
Equal Cut 思路: 枚举中间那个分界点,然后两边找使得切割后差值最小的点,这个可以用双指针 代码: #include<bits/stdc++.h> using namespace ...
- postMan用法
增加: 删除: 更改: 查询:
- Skip level 1 on 1
2019-01-08 16:43:29 Skip level 1:1 什么是 Skip level 1 on 1 :你和你老板的老板(的老板) 1:1 如果你的老板是first line manag ...
- win10+cpu+tensorflow+pycharm
1.安装64位的python3.5 选择windowsx86-64 executable installer安装 2.安装tensorflow cmd->进入到安装python的Scripts文 ...
- Confluence 6 如何考虑设置一个空间的主页
这空间是干什么的?空间主页是访问你空间的用户最先看到的页面.如果你在这个页面中包含一些你空间是干什么的内容能够帮助你的用户更加容易的访问你的空间,同时也能够让你的用户更加容易了解你正在工作的事情.你可 ...
- Kali安装nessus
下载 在官方网站下载对应的 Nessus 版本:http://www.tenable.com/products/nessus/select-your-operating-system 这里选择 Kal ...
- CPU型号各个字母的含义
CPU 型号的含义 首先介绍 4 个数字的含义(以 i7-3540M) 第一位 3540M 中的 "3"代表:代, 3 表示第三代 第二位 3540M 中的 "5&quo ...
- 更改 Windows 软件默认安装位置教程
在打开的“运行”窗口中,输入命令regedit,然后点击确定按钮 计算机\HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion 百度 ...
- 第二阶段——个人工作总结DAY05
1.昨天做了什么:将值由一个活动传递到另一个活动. 2.今天打算做什么:打算制作修改密码的界面. 3.遇到的困难:因为是任务是分开的,所需要获取的值是通过另一个活动(不是自己任务)的传递过来的,所以还 ...
- grep 和curl -d等命令 单引号里面既使用正则,又使用变量的方法
a='{"type":"d_log", "log_format":"d_log", "exclude" ...