【xsy2748】 fly 矩阵快速幂
题目大意:有n个点,m条有向边,其中第i条边需要在ti秒后才出现在图上。
有一个人刚开始呆在1号节点,每秒钟他必须要选择一条从他所在位置走出去的边,走出去(如果没有的话这人就死了)
问你他从1号点走到n号所需的最少时间。
数据范围:n,m≤100,max(ti)≤109
此题貌似是一个套路题
令vis[T][i]表示在时刻T,是否能够到达i号节点
我们可以用O(m)的时间基于vis[T][i]求出vis[T+1][i]。
然而这么搞复杂度直接爆炸了。
我们把vis[T]看做是一个1×n的矩阵,我们构造加入前i+1条边的图的邻接矩阵A(矩阵显然是n×n的)
不难发现vis[T+1]=vis[T]×A,这里的乘法是矩阵乘法。
单次矩乘的复杂度是O(n2),加入矩阵快速幂转移就是O(n2log(ti+1−ti))。
然而这么求我们只会求出vis数组的某一些项,然而某条边被加入后是一直存在的。
不难发现我们只需要在时刻ti+1的基础上再走上n步,就可以知道是否可以在加入这条边后到达终点(结论显然)
然后就没有了
时间复杂度:O(n3logT)
1 #include<bits/stdc++.h> 2 #define M 105 3 #define INF 1234567890 4 using namespace std; 5 6 struct mat{ 7 bool a[M][M]; int n,m; 8 mat(){memset(a,0,sizeof(a));} 9 mat(int nn,int mm){memset(a,0,sizeof(a)); n=nn; m=mm;} 10 void set1(){memset(a,0,sizeof(a)); for(int i=1;i<=n;i++) a[i][i]=1;} 11 friend mat operator *(mat a,mat b){ 12 mat c=mat(a.n,b.m); 13 for(int i=1;i<=a.n;i++) 14 for(int k=1;k<=b.n;k++) if(a.a[i][k]) 15 for(int j=1;j<=a.m;j++) 16 c.a[i][j]|=a.a[i][k]&b.a[k][j]; 17 return c; 18 } 19 friend mat operator ^(mat a,int b){ 20 mat ans=mat(a.n,a.m); ans.set1(); 21 while(b){ 22 if(b&1) ans=ans*a; 23 b=b>>1; a=a*a; 24 } 25 return ans; 26 } 27 }a,b; 28 struct edge{ 29 int u,v,t; 30 void rd(){scanf("%d%d%d",&u,&v,&t);} 31 friend bool operator <(edge a,edge b){return a.t<b.t;} 32 }p[M]; 33 int n,m,ans=INF; 34 int main(){ 35 scanf("%d%d",&n,&m); 36 a=mat(1,n); b=mat(n,n); a.a[1][1]=1; 37 if(n==1) {printf("0\n"); return 0;} 38 for(int i=1;i<=m;i++) p[i].rd(); 39 sort(p+1,p+m+1); 40 for(int i=1;i<=m;i++){ 41 mat hh=a; 42 b.a[p[i].u][p[i].v]=1; 43 for(int j=1;j<=n;j++){ 44 hh=hh*b; 45 if(hh.a[1][n]){ 46 ans=min(ans,p[i].t+j); 47 break; 48 } 49 } 50 if(i<m) a=a*(b^(p[i+1].t-p[i].t)); 51 } 52 if(ans==INF) printf("Impossible\n"); 53 else printf("%d\n",ans); 54 }
分类:
矩阵快速幂
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· AI与.NET技术实操系列:基于图像分类模型对图像进行分类
· go语言实现终端里的倒计时
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 25岁的心里话
· 闲置电脑爆改个人服务器(超详细) #公网映射 #Vmware虚拟网络编辑器
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· 零经验选手,Compose 一天开发一款小游戏!
· 一起来玩mcp_server_sqlite,让AI帮你做增删改查!!