其他分享
首页 > 其他分享> > 1012 小雨坐地铁 分层图 最短路

1012 小雨坐地铁 分层图 最短路

作者:互联网

 链接:https://ac.nowcoder.com/acm/contest/26077/1012
来源:牛客网

题目描述

小雨所在的城市一共有 mmm 条地铁线,分别标号为 1 号线,2 号线,……,m 号线。整个城市一共有 nnn 个车站,编号为 1∼n1 \sim n1∼n 。其中坐 i 号线需要花费 aia_iai​ 的价格,每坐一站就需要多花费 bib_ibi​ 的价格。i 号线有 cic_ici​ 个车站,而且这 cic_ici​ 个车站都已知,如果某一站有多条地铁线经过,则可以在这一站换乘到另一条地铁线,并且能多次换乘。现在小雨想从第 sss 个车站坐地铁到第 ttt 个车站,地铁等待时间忽略不计,求最少花费的价格,若不能到达输出 -1 。(地铁是双向的,所以 sss 可能大于 ttt)

输入描述:

第一行输入四个正整数 n,m,s,tn,m,s,tn,m,s,t,分别表示车站个数,地铁线数,起点站和终点站。
第二行到第 m+1m + 1m+1 行,每行前三个数为 ai,bi,cia_i,b_i,c_iai​,bi​,ci​,分别表示坐 i 号线的价格,i 号线每坐一站多花的价格,i 号线车站个数。接下来 cic_ici​ 个数,表示 i 号线的每一个车站的编号,单调递增。

输出描述:

共一行,一个数表示最小花费,若不能到达输出 -1 
示例1

输入

复制
5 2 1 4
2 2 3 1 3 5
2 1 4 2 3 4 5

输出

复制
7

说明

坐 1 号线:花费 2;

1→31 \rightarrow 31→3:花费 2;

换乘 2 号线:花费 2;

3→43 \rightarrow 43→4:花费 1;

所以最小总花费为 7 。

备注:

1≤n≤103,1≤m≤500,1≤s,t≤n1 \leq n \leq 10^3, 1 \leq m \leq 500,1 \leq s,t \leq n1≤n≤103,1≤m≤500,1≤s,t≤n

1≤ai,bi≤100,1≤ci≤n,∑i=1mci≤1051 \leq a_i,b_i \leq 100,1 \leq c_i \leq n,\sum\limits_{i = 1}^m c_i \leq 10^51≤ai​,bi​≤100,1≤ci​≤n,i=1∑m​ci​≤105

分析

有m条地铁线

n个车站

地铁线每到一个站点需要花费b的金额

每进入一条地铁线需要花费a的金额

一个站点如果有多个地铁线可以换乘(还是要花费a的金额)

给每个站点设置超级源点,并向经过这个站点的地铁线连长度为a的边,表示这个站点可以走到的地铁线

每个地铁线的站点之间也连接长度为b的边。

 

分层图 

将1~n 留给超级源点

每一层的每一个站点:i * n + x

相邻站点连接无向边

站点向超级源点连接长度为 0 的边

超级源点向站点连接长度为 a 的边

然后跑一边dijstra

//-------------------------代码----------------------------

//#define int ll
const int N = 1e6+10,M = 1e5+10;
int n,m,s,t;

int e[N],w[N],ne[N],idx,h[N];

void add(int a,int b,int c) {
    e[idx] = b,ne[idx] = h[a],w[idx] = c,h[a] = idx ++ ;
}
int st,ed;
int dist[N];
bool vis[N];
void dij() {
    ms(dist,0x3f);
    priority_queue<pii,V<pii>,greater<pii>> q;
    q.push({0,st});
    dist[st] = 0;
    while(q.size()) {
        auto t = q.top();q.pop();
        int ver = t.y,W = t.x;
        if(vis[ver]) continue;
        vis[ver] = 1;
        if(ver == ed) {
            cout<<dist[ed]<<endl;rt;
        }
        fe(i,ver) {
            int j = e[i];
            if(vis[j]) continue;
            if(dist[j] > dist[ver] + w[i]) {
                dist[j] = dist[ver] + w[i];q.push({dist[j],j});
            }
        }
    }
    cout<<-1<<endl;
}

void solve()
{
    cin>>n>>m>>st>>ed;
    ms(h,-1);
    fo(i,1,m) {
        int a,b,c,tmp;cin>>a>>b>>c;
        fo(j,0,c-1) {
            int x;cin>>x;
            if(j) {
                add(i*n+x,i*n+tmp,b);//连向相连点
                add(i*n+tmp,i*n+x,b);
            }
            tmp = x;
            add(x + n*i,x,0);//连向超级源点
            add(x,x + n*i,a);
        }
    }
    dij();
}
void main_init() {}
signed main(){
    AC();clapping();TLE;
    cout<<fixed<<setprecision(12);
    main_init();
//  while(cin>>n,n)
//  while(cin>>n>>m,n,m)
//    int t;cin>>t;while(t -- )
    solve();
//    {solve(); }
    return 0;
}

/*样例区


*/

//------------------------------------------------------------

 

标签:坐地铁,int,短路,花费,地铁线,站点,leq,号线,1012
来源: https://www.cnblogs.com/er007/p/16599750.html