POJ 2449 Remmarguts' Date 第k条最短路
这么纠结的一道题,两天。。。光题目就杀死人,题意是t->s,而样例是s->t 无语,
求k条最短路,通过这个题了解了A*算法
光代码敲了两遍 错错错 还以为是系统有问题 ,最后发现自己出现bug
f(x)=g(x)+h(x)启发函数 具体还涉及到反向边求h(x)估计函数 g(x)等 cnt[t]==k找到第K条边等
很神奇!这个题 还得再做 还是不错的
先贴个代码吧
#include<iostream> #include<cstdio> #include<cstring> #include<string> #include<queue> #define inf 1000006 #define MAXN 1001 #define MAXM 100001 using namespace std; int head[MAXN],tail[MAXN],h[MAXN]; int visit[MAXN]; int cnt[MAXN]; int n,m,S,T,K,s_edge; struct Node { int p,g,h; bool operator <(Node B)const { return B.g+B.h<g+h; } }; struct Edge { int to, w,next; }edge[MAXM],edge1[MAXM]; void addedge(int u,int v,int ww) { s_edge++; edge[s_edge].to=v; edge[s_edge].w=ww; edge[s_edge].next=head[u]; head[u]=s_edge; edge1[s_edge].to=u; edge1[s_edge].w=ww; edge1[s_edge].next=tail[v]; tail[v]=s_edge; return ; } void dijkstra() { int i,k,mark,MIN; for(i=1;i<=n;i++) { visit[i]=0; h[i]=inf; } h[T]=0; for(k=1;k<=n;k++)//¿ØÖÆ´ÎÊý { MIN=inf; mark=-1; for(i=1;i<=n;i++) { if(!visit[i]&&MIN>h[i]) { MIN=h[i]; mark=i; } } if(mark==-1)break; visit[mark]=1; int t; for(t=tail[mark];t!=-1;t=edge1[t].next) { if(h[edge1[t].to]>h[mark]+edge1[t].w) h[edge1[t].to]=h[mark]+edge1[t].w; } } return ; } int Astar() { priority_queue<Node>qu; memset(cnt,0,sizeof(cnt)); Node St,Se; St.g=0; St.h=h[S]; St.p=S; qu.push(St); while(!qu.empty()) { St=qu.top(); qu.pop(); cnt[St.p]++; if(cnt[St.p]==K&&St.p==T)return St.g; if(cnt[St.p]>K)continue;//??? int f; for(f=head[St.p];f!=-1;f=edge[f].next) { Se.g=St.g+edge[f].w; Se.h=h[edge[f].to]; Se.p=edge[f].to; qu.push(Se); } } return -1; } int main() { while(~scanf("%d%d",&n,&m)) { int u,v,w,i; s_edge=0; memset(head,-1,sizeof(head)); memset(tail,-1,sizeof(tail)); for(i=1;i<=m;i++) { scanf("%d%d%d",&u,&v,&w); addedge(u,v,w); } scanf("%d%d%d",&S,&T,&K); if(S==T)K++; dijkstra(); int x=Astar(); printf("%d\n",x); } return 0; }