插头DP+矩阵乘法

  m喜闻乐见地达到了10^9级别。。而n<=7,并且没有障碍。。所以列与列之间的转移时一样的。。就可以上矩乘了。

  感觉自己快没救了。。看半天题解还是不懂。。

  http://www.cnblogs.com/staginner/archive/2012/09/14/2684712.html 题解其实讲的很清楚了。。

  在枚举转移的状态的时候想乱了好几次。。2^n枚举的是有没有右插头,处理新出现路径的姿势也和平时不同。。。

  剩下的就是矩乘了。。

 #include<cstdio>
#include<iostream>
#include<cstring>
#define ll long long
using namespace std;
const int maxzt=,modd=;
struct zs1{
int last[],tot;
inline int get(int x){
if(last[x])return last[x];
last[x]=++tot,zt[tot]=x;
return tot;
}
int zt[];
}hm;
int mp[];
int a[][],c[][],b[][],map[][][];
int len[];
int i,j,k,n,m,l; inline void decode(int x){
for(int i=n;i>=;i--)mp[i]=x&,x>>=;
}
bool u[];int id[];
inline int encode(){
int i,x=,cnt=;
memset(u,,);
for(i=;i<=n;mp[i]=id[mp[i]],x=x<<|mp[i],i++)
if(!u[mp[i]]&&mp[i]>)u[mp[i]]=,id[mp[i]]=++cnt;
return x;
} inline bool check(int prezt,int nowzt){
int i,up=,left,pre=,sm=n-;bool r;
decode(prezt);
// for(i=1;i<=n;i++)printf(" %d",mp[i]);printf(" %d\n",prezt);
for(i=;i<=n;i++){
r=(nowzt&(<<(i-)))>,left=mp[i];
// printf(" up:%d r:%d l:%d\n",up,r,left);
if((up&&r&&left)||(!up&&!r&&!left))return ;
if(!up){
if(left&&r)continue;
pre=i;
if(!r)up=mp[i];
if(!left)up=-;
}else{
if(left){
if(left==up&&(i<n||nowzt!=))return ;
if(up>){
mp[pre]=mp[i]=;
for(int j=;j<=n;j++)if(mp[j]==left)mp[j]=up;
}else mp[pre]=mp[i],mp[i]=;
}
if(r){
if(up>)mp[i]=up,mp[pre]=;
else mp[i]=mp[pre]=++sm;
}
if(left||r)up=;
}
}
return up==;
}
inline void prerun(){
int i,j,k;
hm.tot=;memset(hm.last,,sizeof(hm.last));
memset(mp,,sizeof(mp));
hm.get(),
mp[]=mp[n]=,hm.get(encode());//printf(" %d\n",encode());
for(i=;i<=hm.tot;i++){//printf(" %d\n",n) ;
int zt=hm.zt[i];decode(zt);
// for(j=1;j<=n;j++)printf(" %d",mp[j]);puts("");
for(j=;j<(<<n);j++)if(check(zt,j))
k=hm.get(encode()),
map[n][i][k]=;//,printf(" %d %d\n",j,k);
}
len[n]=hm.tot;
}
inline void multoa(){
int i;register int j,k;ll tmp;
for(i=;i<=l;i++)for(j=;j<=l;b[i][j]=tmp%modd,j++)
for(tmp=,k=;k<=l;k++)tmp+=(ll)a[i][k]*a[k][j];
for(i=;i<=l;i++)for(j=;j<=l;j++)a[i][j]=b[i][j];
}
inline void multoc(){
int i;register int j,k;ll tmp;
for(i=;i<=l;i++)for(j=;j<=l;b[i][j]=tmp%modd,j++)
for(tmp=,k=;k<=l;k++)tmp+=(ll)a[i][k]*c[k][j];
for(i=;i<=l;i++)for(j=;j<=l;j++)c[i][j]=b[i][j];
}
int main(){
for(i=;i<=;i++)n=i,prerun();//return 233;
while(scanf("%d",&n)!=EOF){
scanf("%d",&m);
if(n==&&m==){
puts("");continue;
}
if((n&)&&!(m&)){
puts("Impossible");continue;
}
memcpy(a,map[n],sizeof(map[n]));l=len[n];
memset(c,,sizeof(c));
for(i=;i<=l;i++)c[i][i]=;
while(m){
if(m&)multoc();
m>>=;if(m)multoa();
}
if(!c[][])puts("Impossible");else printf("%d\n",c[][]);//return 233;
}
return ;
}

发现我的矩乘比标程的慢了不少。。QAQ

本来要跑150ms的。。然后顺手加了对极限数据、无解的特判。。然后直接0ms吓哭...数据竟然这么水= =

[ZOJ3256] Tour in the Castle的更多相关文章

  1. ZOJ 3256 Tour in the Castle 插头DP 矩阵乘法

    题解 这题是一道非常好的插头题,与一般的按格转移的题目不同,由于m很大,要矩阵乘法,这题需要你做一个按列转移的插头DP. 按列转移多少与按格转移不同,但大体上还是基于连通性进行转移.每一列只有右插头是 ...

  2. 插头DP专题

    建议入门的人先看cd琦的<基于连通性状态压缩的动态规划问题>.事半功倍. 插头DP其实是比较久以前听说的一个东西,当初是水了几道水题,最近打算温习一下,顺便看下能否入门之类. 插头DP建议 ...

  3. DP:0

    小故事: A * "1+1+1+1+1+1+1+1 =?" * A : "上面等式的值是多少" B : *计算* "8!" A *在上面等式 ...

  4. Castle Core 4.0.0 alpha001发布

    时隔一年多以后Castle 项目又开始活跃,最近刚发布了Castle Core 4.0.0 的alpha版本, https://github.com/castleproject/Core/releas ...

  5. 对Castle Windsor的Resolve方法的解析时new对象的探讨

    依赖注入框架Castle Windsor从容器里解析一个实例时(也就是调用Resolve方法),是通过调用待解析对象的构造函数new一个对象并返回,那么问题是:它是调用哪个构造函数呢? 无参的构造函数 ...

  6. AOP之Castle DynamicProxy 动态代理

    这里主要介绍使用castle这个动态代理,在.net一些开源的框架里可以找到它的影子,就连微软的rchard也是使用这个进行方法拦截等可以基于这个进行方法拦截,在这个方面PostSharp算是比较好用 ...

  7. ASP.NET Core 整合Autofac和Castle实现自动AOP拦截

    前言: 除了ASP.NETCore自带的IOC容器外,我们还可以使用其他成熟的DI框架,如Autofac,StructureMap等(笔者只用过Unity,Ninject和Castle). 1.ASP ...

  8. POJ 1637 Sightseeing tour

    Sightseeing tour Time Limit: 1000MS   Memory Limit: 10000K Total Submissions: 9276   Accepted: 3924 ...

  9. Euler Tour Tree与dynamic connectivity

    Euler Tour Tree最大的优点就是可以方便的维护子树信息,这点LCT是做不到的.为什么要维护子树信息呢..?我们可以用来做fully dynamic connectivity(online) ...

随机推荐

  1. #ifdef #else #endif #if #ifndef 的用法

    预编译就是在对源文件进行处理之前(如在语法扫描和分析之前),先处理预处理部分,精简代码,然后再进行编译. 预处理命令有:#include 文件包含.#define 宏定义.以及要重点讲的#if.#if ...

  2. KD树小结

    很久之前我就想过怎么快速在二维平面上查找一个区域的信息,思考许久无果,只能想到几种优秀一点的暴力. Kd树就是干上面那件事的. 别的不多说,赶紧把自己的理解写下来,免得凉了. KD树的组成 以维护k维 ...

  3. bzoj 4198: [Noi2015]荷马史诗

    Description 追逐影子的人,自己就是影子. --荷马 Allison 最近迷上了文学.她喜欢在一个慵懒的午后,细细地品上一杯卡布奇诺,静静地阅读她爱不释手的<荷马史诗>.但是由& ...

  4. 对于group by 和 order by 并用 的分析

    今天朋友问我一个sql查询. 需求是 找到idapi最近那条数据,说明idapi 是重复的,于是就简单的写了 SELECT * FROM `ag_alarm_history`   group by ` ...

  5. rtmp流媒体搭建的所需安装包

    说明:这是基于nginx rtmp控件  搭建的rtmp流媒体服务器,在此附上的是搭建所需要的安装包,具体的搭建过程看我之前的"ubuntu流媒体搭建" 链接地址:http://p ...

  6. 发布 Google Chrome插件教程

    换个视角,世界不一样.嘘~~~ 如果你会使用js的话,那么你就可以自己动手写一个chrome插件,而且非常容易.google是一个全球化的平台,想想自己的程序被世界人民所使用,是不是很激动? 注册开发 ...

  7. 关于md5的使用方法

    本周工作,学习中用到了,md5. 在我们需要用到md5密码的时候,可以使用: System.Web.Security.FormsAuthentication.HashPasswordForStorin ...

  8. Asp.net MVC在Razor中输出Html的两种方式

    http://qubernet.blog.163.com/blog/static/177947284201485104616368/ Razor中所有的Html都会自动编码,这样就不需要我们手动去编码 ...

  9. 执行PHP脚本时遇到 mysql_connect(): Headers and client library minor version mismatch的解决方法

    把服务器从Windows迁移到了centos7.2,配置好PHP运行环境后,项目运行正常. 但在命令行中运行一个PHP脚本时,遇到了标题中显示的错误 使用 php -i | grep Client 得 ...

  10. Nginx编译配置介绍

    源码包 nginx-1.6.2.tar.gz --help 使用帮助 --prefix=PATH Nginx安装路径,如果没有指定,默认为/usr/local/nginx. --sbin-path=P ...