1. 程式人生 > >P1807 最長路_NOI導刊2010提高(07)

P1807 最長路_NOI導刊2010提高(07)

接下來 for pac ext 輸入輸出 etc while out string

洛谷——P1807 最長路_NOI導刊2010提高(07)

題目描述

設G為有n個頂點的有向無環圖,G中各頂點的編號為1到n,且當為G中的一條邊時有i < j。設w(i,j)為邊的長度,請設計算法,計算圖G中<1,n>間的最長路徑。

輸入輸出格式

輸入格式:

輸入文件longest.in的第一行有兩個整數n和m,表示有n個頂點和m條邊,接下來m行中每行輸入3個整數a,b,v(表示從a點到b點有條邊,邊的長度為v)。

輸出格式:

輸出文件longest.out,一個整數,即1到n之間的最長路徑.如果1到n之間沒連通,輸出-1。

輸入輸出樣例

輸入樣例#1:
2 1
1 2 1
輸出樣例#1:
1

說明

20%的數據,n≤100,m≤1000

40%的數據,n≤1,000,m≤10000

100%的數據,n≤1,500,m≤50000,最長路徑不大於10^9

思路:

求最長路??

我們是不是都自然而然的想到了最短路??那好,我們來想一想這個題用最短路怎麽做。。

又沒有人想出來呢??

對!我們只需要我們把數組初始化為-1,然後再跑spfa求最長路就可以了!!

來看看代碼?!

代碼:

#include<queue>
#include<cstdio>
#include
<cstdlib> #include<cstring> #include<iostream> #include<algorithm> #define N 500005 using namespace std; int x,y,z,n,m,tot,b; int head[N],dis[N]; queue<int>q; bool vis[N]; int read() { int x=0,f=1; char ch=getchar(); while(ch<0||ch>9) {if(ch==-
) f=-1; ch=getchar();} while(ch>=0&&ch<=9){x=x*10+ch-0;ch=getchar();} return x*f; } struct Edge { int to,from,dis,next; }edge[N<<2]; void add(int x,int y,int z) { tot++; edge[tot].to=y; edge[tot].dis=z; edge[tot].next=head[x]; head[x]=tot; } int spfa(int a) { for(int i=1;i<=n;i++) dis[i]=-1; dis[a]=0; vis[a]=true; q.push(a); while(!q.empty()) { b=q.front();q.pop(); for(int i=head[b];i;i=edge[i].next) { if(dis[edge[i].to]<edge[i].dis+dis[b]) { dis[edge[i].to]=edge[i].dis+dis[b]; if(!vis[edge[i].to]) q.push(edge[i].to),vis[edge[i].to]=true; } } vis[b]=false; } } int main() { n=read(),m=read(); for(int i=1;i<=m;i++) x=read(),y=read(),z=read(),add(x,y,z); spfa(1); printf("%d",dis[n]); return 0; }

P1807 最長路_NOI導刊2010提高(07)