URAL - 1930

The world is in danger! Awful earthquakes are detected all over the world. Houses are destroyed, rivers overflow the banks, it is almost impossible to move from one city to another. Some roads are still useful, but even they became too steep because of soil movements.
Fortunately, engineer Ivan has a car, which can go well uphill and downhill. But there are different gear-modes for movement up and down, so during the driving you have to change gear-modes all the time. Also engineer Ivan has a good friend –– geologist Orlov. Together they are able to invent a plan for world saving. But, unfortunately, geologist Orlov lives in another town.
Ivan wants to save the world, but gear-box in his car started to wear out, so he doesn’t know, how long he will be able to use it. Please help Ivan to save the world. Find a route to the Orlov's town, such that Ivan will have to change gear-modes as few times as possible. In the beginning of the way Ivan can turn on any of gear-modes and you don't have to count this action as a changing of gear-mode.
Input
There are two positive integer numbers n and m in the first line, the number of towns and roads between them respectively (2 ≤ n ≤ 10 000; 1 ≤ m ≤ 100 000). Next m lines contain two numbers each — numbers of towns, which are connected by road. Moreover, the first is the town, which is situated below, from which you should go uphill by this road. Every road can be used for traveling in any of two directions. There is at most one road between any two cities. In the last line there are numbers of two cities, in which Ivan and geologist Orlov live, respectively. Although the majority of roads were destroyed, Ivan knows exactly, that the way to geologist Orlov's city exists.
Output
Output the smallest number of gear-modes changes on the way to Orlov's city.
Example
inputoutput
3 2
1 2
3 2
1 3
1
3 3
1 2
2 3
3 1
1 3
0

感觉是一个比较裸的最短路,不过当时我没做出来- -!

变形点就是:

1.路径的权值没有告诉你

2.没有二了- -

不过需要加一个数组说明一下当前节点的朝向

当朝向与边权不同的时候这个距离其实就是1,反之为0

很容易表达啊 nowdir[i]^w就可以啊

╮(╯▽╰)╭+++当时没做出来+++╮(╯▽╰)╭

还有一点,一开始的话,走任何节点都是不需要记录值的,所以你需要模拟spfa的第一步,出开始节点,入开始节点的链接节点,并且dist赋值为0;

行了 没了。。。。。。。。。。。。。

#include<bits/stdc++.h>
using namespace std;
struct aa
{
    int u,v,w,next;
} save[200008];
int pre[10086];
int ans=0;
int dist[10086];
bool vis[10086];
int n,m;
int nowdir[10086];
void add(int u,int v,int w)
{
    save[ans].u=u;
    save[ans].v=v;
    save[ans].w=w;
    save[ans].next=pre[u];
    pre[u]=ans++;
}
void init()
{
    for(int i=1; i<=n; i++)
    {
        pre[i]=-1;
        dist[i]=0x3f3f3f3f;
        vis[i]=0;
    }
}
void spfa(int s,int e)
{
    queue<int>ycq;
    dist[s]=0;
    for(int i=pre[s]; i!=-1; i=save[i].next)
    {
        int v=save[i].v;
        int w=save[i].w;
        nowdir[v]=w;
        dist[v]=0;
        ycq.push(v);
        vis[v]=1;
    }
    while(!ycq.empty())
    {
        int u=ycq.front();
        ycq.pop();
        vis[u]=0;
        for(int i=pre[u]; i!=-1; i=save[i].next)
        {
            int v=save[i].v;
            int w=save[i].w;
            if(dist[v]>dist[u]+(nowdir[u]^w))
            {
                dist[v]=dist[u]+(nowdir[u]^w);
                nowdir[v]=w;
                if(!vis[v])
                {
                    vis[v]=1;
                    ycq.push(v);
                }

            }
        }
    }
    printf("%d\n",dist[e]);
}
int main()
{
    while(scanf("%d%d",&n,&m)!=EOF)
    {
        init();
        while(m--)
        {
            int u,v;
            scanf("%d%d",&u,&v);
            add(u,v,1);
            add(v,u,0);
        }
        int a,b;
        scanf("%d%d",&a,&b);
        spfa(a,b);
    }
}



  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值