1 条题解

  • 0
    @ 2025-4-10 15:47:07

    题意:给出n条路 每条路的边权为1 求从1走到k要经过的最少的点的个数 并输出路径

    分析: 最少点的个数 其实就是最短路径+1+1 所以我们可以把源点从11 向前移动一个单位 设为00 那么怎么去记录路径呢? 这里我们可以去开一个数组 记录当前这个点是由哪个点过来的 那么可以一直回溯 回溯到这个数组的初始化 等等 这是不是有点并查集的思想呢? 是的 确实是并查集找父节点的思想 那么我们只要把这个数组初始化 pre[i]=ipre[i]=i 并在dijkstradijkstra中记录该点的父节点即可 代码:

    #include<iostream>
    #include<vector>
    #include<cstdio>
    #include<queue>
    using namespace std;
    typedef long long ll;
    struct node
    {
        int from,to,cost;
        node() {}
        node(int t,int q,int w):from(t),to(q),cost(w) {}
        friend bool operator <(const node &a, const node &b)
        {
            return a.cost>b.cost;
        }
    };
    vector<node> v[1005];
    bool vis[1005];
    int pre[1005];
    int dis[1005];
    void dijkstra(int y)
    {
    
        priority_queue<node>q;
        q.push(node(0,1,1));///因为要输出的是点的个数 那么我们可以把0设为源点 
    
        while(q.size())
        {
    
            node now=q.top();
            q.pop();
            if(!vis[now.to])
            {
                vis[now.to]=1;
                ///下面这里十分关键 也是容易错的地方 
                ///dis和pre的赋值一定要在这里 原因的话请读者仔细思考
                pre[now.to]=now.from;///记录当前点的父节点
                dis[now.to]=now.cost;
                for(int i=0; i<v[now.to].size(); i++)
                {
    
                    node next=now;
                    next.to=v[now.to][i].to;
                    if(!vis[next.to])
                    {
                        next.from=now.to;
                        next.cost+=v[now.to][i].cost;
                        q.push(next);
    
                    }
                }
            }
    
        }
        if(dis[y]==~0u>>1)
            puts("-1");
        else
        {
            cout<<dis[y]<<endl;
            vector<int>b;
            while(pre[y]!=y)///存路径
                b.push_back(y),y=pre[y];
    
            for(int i=b.size()-1; i>=0; i--)///因为路径从父节点开始走的 倒着输出
                cout<<b[i]<<endl;
        }
    
    }
    int main()
    {
    
        int n,k;
        while(cin>>n>>k)
        {
    
            for(int i=0; i<=1005; i++)
                v[i].clear(),vis[i]=0,pre[i]=i,dis[i]=~0u>>1;
    
            int a,b;
            for(int i=1; i<=n; i++)
            {
                cin>>a>>b;
                v[a].push_back(node(a,b,1));
            }
    
            dijkstra(k);
        }
        return 0;
    }
    
    
    • 1

    信息

    ID
    1459
    时间
    1000ms
    内存
    64MiB
    难度
    (无)
    标签
    递交数
    0
    已通过
    0
    上传者