zoukankan      html  css  js  c++  java
  • 最短路(三种基础算法)

    蒟蒻最近在不断AK最短路

    这篇博客就发一下最基础的三种做法(以后会发一篇升级版的

    1.大名鼎鼎的Floyd

    2.Dijkstra

    3.Bellman-Ford

    就以这道题为例吧

    (这道题数据苛(hen)刻(shui),不过代码已用大数据测过,不要怀疑算法的准确性)

    注:三种算法我写在了一起

    #include<bits/stdc++.h>
    using namespace std;
    struct node{
        int x,y;
    }a[150];
    double dis[150][150],f[150];
    int n,m,s,t;
    
    void init_1()
    {
        
        cin>>n;
        for(int i=1;i<=n;i++)
            cin>>a[i].x>>a[i].y;
        cin>>m;
        memset(dis,0x7f,sizeof(dis));
        for(int i=1;i<=m;i++)
        {
            int u,v;
            cin>>u>>v;
            dis[u][v]=sqrt(pow(a[u].x-a[v].x,2)+pow(a[u].y-a[v].y,2));
            dis[v][u]=dis[u][v];
        }
        cin>>s>>t;
    }
    
    
    void Floyd()
    {
        for(int k=1;k<=n;k++)
        for(int i=1;i<=n;i++)
        for(int j=1;j<=n;j++)
        dis[i][j]=min(dis[i][j],dis[i][k]+dis[k][j]);
        printf("%.2lf",dis[s][t]);
    }
    
    
    bool used[150];
    void Dj()
    {
        memset(f,0x7f,sizeof(f));
        f[s]=0;
        for(int i=1;i<=n-1;i++)
        {
            int k=0;
            double minn=1e30;
            for(int j=1;j<=n;j++)
            if(!used[j] && f[j]<=minn)
            minn=f[j],k=j;
            if(k==0) break;
            used[k]=true;
            for(int j=1;j<=n;j++)
            if(!used[j])
            f[j]=min(f[j],dis[j][k]+minn);
        }
        printf("%.2lf",f[t]);
    }
    
    double w[15000];
    int u[15000],v[15000];
    void init_2()//B-F算法的输入记录的是边,要特殊处理 
    {
        cin>>n;
        for(int i=1;i<=n;i++)
            cin>>a[i].x>>a[i].y;
        cin>>m;
        memset(f,0x7f,sizeof(f));
        for(int i=1;i<=m;i++)
        {
            cin>>u[i]>>v[i];
            w[i]=sqrt(pow(a[u[i]].x-a[v[i]].x,2)+pow(a[u[i]].y-a[v[i]].y,2));
        }
        cin>>s>>t;
    }
    
    void Bellman_Ford()
    {
        f[s]=0;
        for(int k=1;k<=n-1;k++)
        {
           bool p=true;//一点小优化
          for(int i=1;i<=m;i++)
          {
            if(f[v[i]]+w[i]<f[u[i]])
                f[u[i]]=f[v[i]]+w[i],p=false; 
            else
            if(f[u[i]]+w[i]<f[v[i]])
                f[v[i]]=f[u[i]]+w[i],p=false;
           }
            if(p) break;
        }
        
        printf("%.2lf",f[t]);
    }
    int main()
    {
        init_2();
        Bellman_Ford();
        ////init_1();
        //Dj();
        return 0;
    }

    添加一个SPFA大法

    添加时间:2019-5-17

    #include<bits/stdc++.h>
    using namespace std;
    const int INTMAX=2147483647,MAX=500050;
    struct node{
        int next;
        int to;
        int w;
    }a[MAX];
    int f[MAX],head[10050];
    int n,m,s,tot;
    bool b[10050];
    queue<int> q;
    void add(int,int,int);
    void init()
    {
        cin>>n>>m>>s;
        memset(f,0x7f,sizeof(f));
        for(int i=1;i<=m;i++)
        {
            int u,v,w;
            cin>>u>>v>>w;
            add(u,v,w);
        }
        
    }
    
    void add(int u,int v,int w)
    {
        tot++;
        a[tot].next=head[u];
        a[tot].to=v;
        a[tot].w=w;
        head[u]=tot;
    }
    
    void print()
    {
        for(int i=1;i<=n;i++)
        if(f[i]<2e9)
        cout<<f[i]<<" ";
        else cout<<INTMAX<<" ";
        cout<<endl;
    }
    
    
    
    void SPFA()
    {
        f[s]=0;
        q.push(s);
        b[s]=true;
        while(!q.empty())
        {
          int u;
          u=q.front();
          q.pop();
          b[u]=false;
          for(int i=head[u];i;i=a[i].next)
          {
              int v=a[i].to;
              if(f[v]>f[u]+a[i].w)
              {
                  f[v]=f[u]+a[i].w;
                  if(!b[v])
                  {
                      b[v]=true;
                    q.push(v);    
                }
            }
          }
    //      for(int i=1;i<=m;i++)
    //        if(f[u[i]]+w[i]<f[v[i]])
    //            f[v[i]]=f[u[i]]+w[i],p=false; 
        }
        print();
    }
    
    int main()
    {
        init();
        SPFA();
        return 0;
    }
  • 相关阅读:
    排序算法整理
    V-REP Plugin 开发
    YAML-CPP
    YAML
    V-REP Remote API
    V-REP Plugin
    结构化方法与面向对象方法的比较
    敏捷软件开发vs传统软件工程
    个人项目-地铁出行路线规划程序
    Week1个人作业
  • 原文地址:https://www.cnblogs.com/zhouzhihao/p/10847108.html
Copyright © 2011-2022 走看看