SPFA

SPFA与dijkstra算法的区别

1. dijkstra算法是含贪心思想,SPFA更像BFS

2.BFS每个点只入对一次,而SPFA一个点在出了队列之后,可能会重新入队,在本身改进后,用来改进其他点。

3.SPFA可以处理负权边,每个点入队次数超过N,则存在负权环

代码:

View Code
//邻接表存储图的最短路 
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <iostream>
#include <queue>
using namespace std;

#define MAXN 100100
struct Edge
{
  int u, next, val;
  Edge() {}
  Edge( int v , int Next ,int Val): u(v),next(Next), val(Val) { }      
}edge[MAXN];

const int inf = 0x7f7f7f7f;
int head[MAXN],dis[MAXN], visit[MAXN], size, S, T, N, M;


struct node
{
  int ID,dis;
};

void init( )
{
  for( int i = 0; i <= N; i++)
  {
       head[i] = -1;
       visit[i] = 0;
       dis[i] = inf;
  }
  size = 0;
       
}

void AddEdge( int u, int v, int val)
{
   edge[size] = Edge( v, head[u], val);
   head[u] = size++;
   
   edge[size] = Edge( u, head[v], val);
   head[v] = size++;
     
}


int SPFA( )
{
   queue<node>q;
   node p;
   p.ID = S;
   p.dis = 0;
   q.push(p);
   dis[S] = 0;
   while( !q.empty( ))
   {  
       p = q.front( );
       q.pop();
       int v = p.ID;
       int wx = dis[v];
       visit[v] = 0;
       for( int e = head[v]; e != -1; e = edge[e].next)
       {  
          int u = edge[e].u;
          int w = edge[e].val;
          if( dis[u] > wx + w )
          {
               dis[u] = wx + w;
               if( !visit[u] )
               {    
                 p.ID = u;
                 p.dis = dis[u];
                 visit[u] = 1;
                 q.push( p );
               }
                
          }  
            
       }
   }
   return dis[T];
} 
        

    
    

int main( )
{
  int a, b, c;
  while( scanf("%d%d", &N, &M), N + M)
  {
     init( );
     for( int i = 1; i <= M; i++)
     {
         scanf("%d%d%d",&a, &b, &c);
         AddEdge(a, b, c);   
     } 
     S = 1;
     T = N;      
     printf("%d\n", SPFA());
  }      
  return 0;  
}

posted on 2012-07-10 09:31  more think, more gains  阅读(192)  评论(0编辑  收藏  举报

导航