2020牛客暑期多校训练营(第二场) I Interval

思路:很明显最小割,但直接跑Dinic一定会超时,所以要将原图转化成对偶图来跑最短路,至于怎么转化,建议去搜其他人的博客。

#include <cstdio>
#include <algorithm>
#include <queue>
#include <stack>
#include <string>
#include <string.h>
#include <map>
#include <iostream>
// std::ios::sync_with_stdio(false);
// ios::sync_with_stdio(false);

using namespace std;
typedef long long LL;
typedef unsigned long long ULL;
typedef pair<int, int> pii;
typedef pair<pii, int> piii;
const int maxn = 3e6 + 50;
const LL mod = 998244353;
LL INF = 1e15;

#define fi first
#define se second
int n, m;
map<pii, int> mmap, mmap2;
struct Edge
{
    int to, next;
    LL w;
} edge[maxn];
int k, head[maxn];
void add(int a, int b, int w){
    if(mmap2[{a, b}]) return ;
    edge[k].to = b, edge[k].w = w, edge[k].next = head[a], head[a] = k++;
    edge[k].to = a, edge[k].w = w, edge[k].next = head[b], head[b] = k++;
}


struct qnode
{
    int u;
    LL c;
    bool operator < (const qnode &r) const{
        return c > r.c;
    }
};

priority_queue<qnode> que;
LL dis[maxn];
int vis[maxn];
void dj(int s, int t){
    for(int i = 0; i <= t; i++) dis[i] = INF;
    que.push({s, 0});
    dis[s] = 0;
    while(que.size()){
        qnode tmp = que.top();
        que.pop();
        int u = tmp.u;
        if(tmp.c != dis[u]) continue;
        for(int i = head[u]; i != -1; i = edge[i].next){
            int to = edge[i].to;
            if(dis[to] > dis[u] + edge[i].w){
                dis[to] = dis[u] + edge[i].w;
                que.push({to, dis[to]});
            }
        }
    }
    if(dis[t] == INF) printf("-1\n");
    else printf("%lld\n", dis[t]);
}
int main(int argc, char const *argv[])
{
    scanf("%d%d", &n, &m);
    LL sum = 0;
    int s = 0, t = n * n * 10;
    for(int i = 0; i <= t; i++){
        head[i] = -1;
    }
    int cnt = 0;
    for(int i = 1; i <= n; i++){
        for(int j = 1; j <= n; j++){
            mmap[{i, j}] = ++cnt;
        }
    }
    for(int i = 1; i <= m; i++){
        int le, ri;
        LL c;
        char ch;
        scanf("%d%d %c%lld", &le, &ri, &ch, &c);
        sum += c;
        if(ch == 'L'){
            if(ri == n) add(0, le * n + ri - 1, c);
            else add(le * n + ri - 1, le * n + ri, c);
        } else {
            if(le == 1) add(le * n + ri - 1, t, c);
            else add(le * n + ri - 1, (le - 1) * n + ri - 1, c);
        }
    }

    dj(s, t);
    return 0;
}



posted @ 2020-07-14 19:03  从小学  阅读(230)  评论(0编辑  收藏  举报