Find the monotone shortest path in a graph in O (E logV)

Problem 34 creative problems from this page .

Monotonic shortest path. . Given a given boundary digraph, find the monotonous shortest path from s to any other vertex. A path is monotonous if the weight of each edge on the path either strictly increases or strictly decreases.

Partial solution : relax the edges in ascending order and find the best way; then relax the edges in descending order and find the best way.

My question is:

Suppose we relax the edges in descending order, and we have a choice of more than 1 edge to be taken at a point. On what basis will we choose the next edge? Ideally, we should choose a smaller edge, since it minimizes the distance to this peak. But doing this may not lead to further paths from this vertex if all the remaining edges have a weight that is greater than the current edge weight.

So how can we solve this problem?

+4
source share
1 answer

. , min node ( ), .

. , ( , 2 4):

  • node ( ).
  • node ( ).
  • , "" ( -). , , ( ​​ ). ( ), . , .
  • : - (, , , ) ; , , node, , , .

, ( , , ), O (E log E).

++ 11:

void getDecreasingSP(Vertices& vertices, Edges& edges, int src)
{
    for (auto& v: vertices)
        sort(begin(v.outEdges), end(v.outEdges),
             [&](int from, int to)
             {
                 return edges[from].weight < edges[to].weight;
             });

    PQ pq;
    auto& src_v = vertices[src];
    for (auto e: src_v.outEdges)
    {
        QEntry entry {edges[e].weight, e};
        pq.push(entry);
        ++src_v.pos;
    }

    while(!pq.empty())
    {
        QEntry top = pq.top();
        pq.pop();
        auto& v = vertices[edges[top.inEdge].to];

        while (v.pos < int(v.outEdges.size()) &&
            edges[v.outEdges[v.pos]].weight < edges[top.inEdge].weight)
        {
            auto e = v.outEdges[v.pos];
            edges[e].backPtr = top.inEdge;
            QEntry entry {top.pathWeight + edges[e].weight, e};
            pq.push(entry);
            ++v.pos;
        }

        if (v.backPtr == -1)
            v.backPtr = top.inEdge;
    }
}

. Ideone. ( Graphviz), :

enter image description here

+4

Source: https://habr.com/ru/post/1535136/


All Articles