[FZU1977] Pandora adventure
来学插头DP了= =
GDKOI前觉得不会考数位DP,GDOI前觉得插头DP用不上。。
结果令人伤感>_<
这题并不用增加状态。。
只要在形成环的时候,让形成环的位置在最后一个必走点之后,并且此时只有一个联通分量。
因为必走点处肯定有插头。。所以只有一个联通分量就意味着所有必走点都连在一起了。
选择经过的点就在转移的时候多一种方法。。。
学的是最小表示法。。又长又慢TAT。。跳错坑了= =
#include<cstdio>
#include<iostream>
#include<cstring>
#define ull unsigned long long
using namespace std;
const int modd=,maxzt=;
struct zs{
struct hash{
ull too;int pre;
}e[maxzt];int tot,last[modd];
ull f[maxzt],zt[maxzt]; inline int get(ull v){
int i,x=v%modd;
for(i=last[x];i&&e[i].too!=v;i=e[i].pre);
if(i&&e[i].too==v)return i;
e[++tot].too=v,e[tot].pre=last[x],last[x]=tot;
zt[tot]=v;f[tot]=;
return tot;
}
}hm[];
int i,j,k,n,m,tx,ty;
int can[][];
ull ans;
char s[];
int v[]; inline void clr(bool now){
memset(hm[now].last,,modd<<),
hm[now].tot=;
} bool u[];int id[],mp[];
inline ull encode(){
memset(u,,);
ull x=;int tt=;
for(int i=;i<=m;mp[i]=id[mp[i]],x=x<<|mp[i],i++)
if(mp[i]&&!u[mp[i]])u[mp[i]]=,id[mp[i]]=++tt;
return x;
}
inline void decode(ull x){
for(int i=m;i>=;i--)mp[i]=x&,x>>=;
}
inline void shift(){
for(int i=m;i;i--)mp[i]=mp[i-];
mp[]=;
} inline void dp_blank(int x,int y,bool pre){
int i,left,up,j;bool now=pre^;ull zt,f;
clr(now);
for(i=;i<=hm[pre].tot;i++){
zt=hm[pre].zt[i],f=hm[pre].f[i],
decode(zt);
left=mp[y-],up=mp[y];
if(!left&&!up){
if(can[x+][y]&&can[x][y+]){
mp[y-]=mp[y]=;
if(y==m)shift();
hm[now].f[ hm[now].get(encode()) ]+=f;
}
if(can[x][y]==){
mp[y-]=mp[y]=;
if(y==m)shift();
hm[now].f[ hm[now].get(encode()) ]+=f;
}
}
if((!left)^(!up)){
j=left|up;
if(can[x+][y]){
mp[y-]=j,mp[y]=;
if(y==m)shift();
hm[now].f[ hm[now].get(encode()) ]+=f;
}
if(can[x][y+]){
mp[y-]=,mp[y]=j;
if(y==m)shift();
hm[now].f[ hm[now].get(encode()) ]+=f;
}
}
if(left&&up){
if(left==up)
if(x>tx||(x==tx&&y>=ty)){
mp[y-]=mp[y]=;
if(encode()==)ans+=f;
}else;
else{
mp[y-]=mp[y]=;
for(j=;j<=m;j++)if(mp[j]==up)mp[j]=left;
if(y==m)shift();
hm[now].f[ hm[now].get(encode()) ]+=f;
}
}
}
}
inline void dp_bar(int x,int y,bool pre){
int i,left,up;bool now=pre^;ull f,zt;
clr(now);
for(i=;i<=hm[pre].tot;i++){
zt=hm[pre].zt[i],f=hm[pre].f[i];
decode(zt);
left=mp[y-],up=mp[y];
if(!left&&!up){
if(y==m)shift();
hm[now].f[ hm[now].get(encode()) ]+=f;
}
}
} int main(){
int TT;
scanf("%d",&TT);v['X']=,v['O']=,v['*']=;
for(int TTT=;TTT<=TT;TTT++){
scanf("%d%d",&n,&m);
memset(can,,sizeof(can));
for(i=;i<=n;i++)
for(scanf("%s",s+),j=;j<=m;j++){
can[i][j]=v[s[j]];
if(s[j]=='O')tx=i,ty=j;
} for(i=n,j=;i;i--){
for(j=m;j;j--)if(can[i][j]==)break;
if(j>)break;
}
tx=i,ty=j; bool now=,pre=;ans=;
clr(),hm[pre].f[ hm[pre].get() ]=;
for(i=;i<=n;i++)for(j=;j<=m;j++,swap(now,pre))
if(can[i][j])dp_blank(i,j,pre);else dp_bar(i,j,pre);
printf("Case %d: %I64u\n",TTT,ans);
}
return ;
}
[FZU1977] Pandora adventure的更多相关文章
- FZU1977 Pandora adventure —— 插头DP
题目链接:https://vjudge.net/problem/FZU-1977 Problem 1977 Pandora adventure Accept: 597 Submit: 2199 ...
- 【FZU】1977 Pandora adventure
http://acm.fzu.edu.cn/problem.php?pid=1977 题意:n×m的网格,有3种格子,'O'必须经过.'*'可以选择经过.'X'不能经过.现在要求路径经过所有'O'且是 ...
- FZU 1977 Pandora adventure (DP)
题意:给定一个图,X表示不能走,O表示必须要走,*表示可走可不走,问你多少种走的法,使得形成一个回路. 析: 代码如下: #pragma comment(linker, "/STACK:10 ...
- FZU 1977 Pandora adventure (插头DP,常规)
题意:有一个n*m矩阵,其中有些格子必走,有些格子不可走,其他格子是可走也可不走,问有多少条哈密顿回路? 思路: 本来是一道很简单的题,代码写多了连白痴bug都查不出了,竟然用i>=ex& ...
- 插头DP专题
建议入门的人先看cd琦的<基于连通性状态压缩的动态规划问题>.事半功倍. 插头DP其实是比较久以前听说的一个东西,当初是水了几道水题,最近打算温习一下,顺便看下能否入门之类. 插头DP建议 ...
- DP:0
小故事: A * "1+1+1+1+1+1+1+1 =?" * A : "上面等式的值是多少" B : *计算* "8!" A *在上面等式 ...
- 插头dp练习
最近学了插头dp,准备陆续更新插头dp类练习. 学习论文还是cdq那篇<基于连通性状态压缩的动态规划问题>. 基本的想法都讲得很通透了,接下来就靠自己yy了. 还有感谢kuangbin大大 ...
- HDU 3377 Plan (插头DP,变形)
题意:有一个n*m的矩阵,每个格子中有一个值(可能负值),要从左上角走到右下角,求路径的最大花费. 思路: 除了起点和终点外,其他的点可以走,也可以不走. (2)我用的是括号表示法,所以起始状态为') ...
- Java基础-接口看下图实现如下接口和类,并完成Adventure中的主方法
package hanqi; public interface CanSwim { void swim(); } package hanqi; public interface CanFly { pu ...
随机推荐
- Ubuntu14.04下安装 boost (boost_1.54 最简单的方法)
直接执行命令: sudo apt-get install libboost-dev 测试: 创建一个 boost_test.cpp 文件,写入 #include<iostream> #i ...
- KVM 初探
KVM 是业界最为流行的 Hypervisor,全称是 Kernel-based Virtual Machine.它是作为 Linux kernel 中的一个内核模块而存在,模块名为 kvm.ko,也 ...
- 尝试在条件“$(_DeviceSdkVersion) >= 21”中对计算结果为“”而不是数字的“$(_DeviceSdkVersion)
晚上搞xamarin ,运行xamarin项目好好的,不知道怎么回事,一次运行xamarin android项目的时候,部署失败,以前也是遇到这样的错误. 尝试在条件"$(_DeviceSd ...
- AntData.ORM框架 之 读写分离
环境准备 准备2台机器配置好Master Slaver模式 我是用vmware 2台虚拟机配置的.有需要请联系. Master:192.168.11.130 Slaver:192.168.11.133 ...
- NOI 2008 假面舞会
题目描述 一年一度的假面舞会又开始了,栋栋也兴致勃勃的参加了今年的舞会. 今年的面具都是主办方特别定制的.每个参加舞会的人都可以在入场时选择一 个自己喜欢的面具.每个面具都有一个编号,主办方会把此编号 ...
- collections --Counter
collections 模块--Counter 目的是用来跟踪值出现的次数.是一个无序的容器类型,以字典的键值对形式存储,其中元素为 key,其计数作为 value.计数值可以是任意的 Integer ...
- python利用pysvn发布lib的小程序
背景: 本人在公司的平台部门工作,我们部门写出的代码都是编译成.a文件,定期发布版本到各个产品,现在老大要求我负责每周向公司的某个产品发布lib.发布lib的步骤大概就是自动化的兄弟给我提供一个归档的 ...
- leetcode — linked-list-cycle-ii
/** * Source : https://oj.leetcode.com/problems/linked-list-cycle-ii/ * * Given a linked list, retur ...
- Optimize For Ad Hoc Workloads
--临时工作负载优化 即席查询:也就是查询完没放到Cache当中,每次查询都要重新经过编译,并发高的时候很耗性能: 参数化查询: 一方面解决了重编译问题,但随着数据库数据数据的变更,统计信息的更新 ...
- 用 HAproxy 搭建 RabbitMQ 集群
构建参考: [ Rabbitmq cluster setup with HAproxy ] [ python demo ] RabbitMQ Cluster 遇到的问题 python pika 作为c ...