• 【洛谷 2136】拉近距离


    题目背景

    我是源点,你是终点。我们之间有负权环。 ——小明

    题目描述

    在小明和小红的生活中,有N个关键的节点。有M个事件,记为一个三元组(Si,Ti,Wi),表示从节点Si有一个事件可以转移到Ti,事件的效果就是使他们之间的距离减少Wi。

    这些节点构成了一个网络,其中节点1和N是特殊的,节点1代表小明,节点N代表小红,其他代表进展的阶段。所有事件可以自由选择是否进行,但每次只能进行当前节点邻接的。请你帮他们写一个程序,计算出他们之间可能的最短距离。

    输入格式

    第1行,两个正整数N,M.

    之后M行,每行3个空格隔开的整数Si,Ti,Wi。

    输出格式

    一行,一个整数表示他们之间可能的最短距离。如果这个距离可以无限缩小,输出“Forever love”(不含引号)。

    输入输出样例

    输入 #1
    3 3
    1 2 3
    2 3 -1
    3 1 -10
    输出 #1
    -2

    说明/提示

    对于20%数据,N<=10,M<=50。

    对于50%数据,N<=300,M<=5000。

    对于全部数据,N<=1000,M<=10000,|Wi|<=100,保证从节点1到N有路径。

    题解:spfa还没死,继续spfa肝题

    #include<cstdio>
    #include<iostream>
    #include<cmath>
    #include<cstring>
    #include<cstdlib>
    #include<algorithm>
    #include<queue>
    using namespace std;
    const int N=20002;
    const string out="Forever love";
    int cnt,x,y,z,n,m,ok[N];
    struct node{
        int next;
        int to;
        int val;
    }e[N];
    int head[N],dis[N],vis[N];
    void add(int x,int y,int z){
        e[++cnt].val=z; e[cnt].to=y;
        e[cnt].next=head[x]; head[x]=cnt;
    }
    int flag=0;
    void spfa(int jjj){
        queue<int>q;
        memset(dis,0x3f,sizeof(dis));
        q.push(jjj); vis[jjj]=1; dis[jjj]=0;
        while(!q.empty()){
            x=q.front(); q.pop(); vis[x]=0;
            if(ok[x]>n){
                cout<<out<<endl;exit(0);
                flag=1; return ;
            }
            for(int i=head[x];i;i=e[i].next){
                y=e[i].to;
                if(dis[y]>dis[x]+e[i].val){
                    dis[y]=dis[x]+e[i].val;
                    if(vis[y]==0) 
                       { q.push(y); ok[y]++; vis[y]=1; } 
                }
            }
        }
        return ;
    }
    
    int main(){
        freopen("2136.in","r",stdin);
        freopen("2136.out","w",stdout);
        scanf("%d %d",&n,&m);
        for(int i=1;i<=m;i++){
            scanf("%d %d %d",&x,&y,&z);
            add(x,y,-z);  
        }
        if(flag==1) return 0;
        spfa(1); int s1=dis[n];
        spfa(n); int s2=dis[1];
        printf("%d",min(s1,s2));
        return 0;
    }
  • 相关阅读:
    win10 visual studio 2017环境中安装CUDA8
    UEFI+GPT电脑Win10下安装openSUSE Leap 42.2双系统
    CentOS7安装PPTP
    Python基础-三元运算
    Python基础-字典dict
    Python基础-元组tuple
    Python基础-列表list
    Python基础-str类型
    Python基础-int类型方法
    Python基础-查看对象的类或对象所具备的功能
  • 原文地址:https://www.cnblogs.com/wuhu-JJJ/p/11810695.html
Copyright © 2020-2023  润新知