237. 程序自动分析

离散化+并查集
复杂度:(O(Tnlogn))
被函数名给坑了,因为二分和并查集都习惯用find函数。。。

#include<iostream>
#include<vector>
#include<algorithm>

using namespace std;

const int N = 2000010;

struct Edge{
    int i, j, e;
    bool operator <(const Edge &ed){
        return e > ed.e;
    }
};

int p[N];
int n;
int k;
vector<int> v;
vector<Edge> edges;

int get(int x){ // 得到值x的位置
    int l = 0, r = k - 1;
    while(l < r){
        int mid = l + r >> 1;
        if(v[mid] >= x) r = mid;
        else l = mid + 1;
    }
    
    return l;
}

int find(int x){
    if(p[x] != x) p[x] = find(p[x]);
    return p[x];
}


int main(){
    int T;
    cin >> T;
    
    while(T --){
        cin >> n;
        
        v.clear();
        edges.clear();
        k = 0;
        
        for(int i = 0; i < n; i ++){
            int x, y, e;
            cin >> x >> y >> e;
            
            v.push_back(x);
            v.push_back(y);
            
            edges.push_back({x, y, e});
        }
        
        sort(v.begin(), v.end());
        sort(edges.begin(), edges.end());
        
        // 去重
        for(int i = 0; i < v.size(); i ++)
            if(i == 0 || v[i] != v[i - 1]) v[k ++] = v[i];
        
        for(int i = n * 2 - 1; i >= 0; i --) p[i] = i;
        
        int flag = 0;
        
        for(auto t : edges){
            int i = get(t.i), j = get(t.j), e = t.e;
            if(e) p[find(j)] = find(i);
            else if(find(j) == find(i)){
                flag = 1;
                break;
            }
        }
        
        if(flag) puts("NO");
        else puts("YES");
    }
    
    return 0;
}
原文地址:https://www.cnblogs.com/tomori/p/13886783.html