Age of Moyu
Time Limit: 5000/2500 MS (Java/Others) Memory Limit: 262144/262144 K (Java/Others)
Total Submission(s): 272 Accepted Submission(s): 58
Problem Description
Mr.Quin love fishes so much and Mr.Quin’s city has a nautical system,consisiting of N ports and M shipping lines. The ports are numbered 1 to N. Each line is occupied by a Weitian. Each Weitian has an identification number.
The i-th (1≤i≤M) line connects port Ai and Bi (Ai≠Bi) bidirectionally, and occupied by Ci Weitian (At most one line between two ports).
When Mr.Quin only uses lines that are occupied by the same Weitian, the cost is 1 XiangXiangJi. Whenever Mr.Quin changes to a line that is occupied by a different Weitian from the current line, Mr.Quin is charged an additional cost of 1 XiangXiangJi. In a case where Mr.Quin changed from some Weitian A's line to another Weitian's line changes to Weitian A's line again, the additional cost is incurred again.
Mr.Quin is now at port 1 and wants to travel to port N where live many fishes. Find the minimum required XiangXiangJi (If Mr.Quin can’t travel to port N, print −1 instead)
Input
There might be multiple test cases, no more than 20. You need to read till the end of input.
For each test case,In the first line, two integers N (2≤N≤100000) and M (0≤M≤200000), representing the number of ports and shipping lines in the city.
In the following m lines, each contain three integers, the first and second representing two ends Ai and Bi of a shipping line (1≤Ai,Bi≤N) and the third representing the identification number Ci (1≤Ci≤1000000) of Weitian who occupies this shipping line.
Output
For each test case output the minimum required cost. If Mr.Quin can’t travel to port N, output −1 instead.
Sample Input
3 3
1 2 1
1 3 2
2 3 1
2 0
3 2
1 2 1
2 3 2
Sample Output
1
-1
2
Source
2018 Multi-University Training Contest 7
Recommend
chendu | We have carefully selected several similar problems for you: 6396 6395 6394 6393 6392
思路:这道题就是用分层的思想,看当前的这个点所能扩展的范围最多到多少,一个点最多走一次,一条边也最多走一次。
走到n就停止。
思想很好!!!
代码:
#include<bits/stdc++.h>
using namespace std;
const int maxm=200000+100;
const int maxn=100000+100;
int cnt,xpp;
queue<int>q;
int n,m;
int d[maxn];
int head[maxn];
struct node{
int v,val,next,flag;
}G[maxm*2];
int init()
{
cnt=0;
xpp=-1;
memset(G,0,sizeof(G));
memset(d,-1,sizeof(d));
memset(head,-1,sizeof(head));
}
void dfs(int rt,int val,int length)
{
if(rt==n){
xpp=length;
return;
}
if(d[rt]==-1)///这个点没有访问过
{
d[rt]=length;///到达这个点的最小步
q.push(rt);
}
for(int i=head[rt];i!=-1;i=G[i].next){
int v=G[i].v;
if(G[i].flag)///这个bian访问过
continue;
if(G[i].val==val)///这个边的val
{
G[i].flag=1;///这个边访问过
dfs(v,val,length);///
}
if(xpp>0)
return ;
}
}
int bfs(){
while(!q.empty())
q.pop();
q.push(1);
d[1]=0;
///G[1].flag=1;
while(!q.empty())
{
int lala=q.front();
q.pop();
for(int i=head[lala];i!=-1;i=G[i].next){///i是边
if(G[i].flag){ ///说明i这个bian走过
continue;
}
int v=G[i].v;
G[i].flag=1;
dfs( v , G[i].val , d[lala]+1 );
if( xpp>0 )
return xpp;
}
if( xpp>0 )
return xpp;
}
return xpp;
}
int main()
{
int a,b,c;
while(~scanf("%d%d",&n,&m)){
init();
for(int i=1;i<=m;i++){
scanf("%d%d%d",&a,&b,&c);
G[++cnt].v=b;
G[cnt].val=c;
G[cnt].flag=0;
G[cnt].next=head[a];
head[a]=cnt;
G[++cnt].v=a;
G[cnt].val=c;
G[cnt].flag=0;
G[cnt].next=head[b];
head[b]=cnt;
}
int kaka=bfs();
printf("%d\n",kaka);
}
}
/*
3 3
1 2 1
1 3 2
2 3 1
2 0
3 2
1 2 1
2 3 2
*/