Submission #1361895

#TimeUsernameProblemLanguageResultExecution timeMemory
1361895ivazivaLove Polygon (BOI18_polygon)C++20
0 / 100
241 ms26448 KiB
#include <bits/stdc++.h>

using namespace std;

#define MAXN 100001
#define int long long

int n;
set<pair<string,string>> edges;
vector<string> kompresija;
vector<int> adj[MAXN];
int parent[MAXN];
vector<int> topolosko;
int idx[MAXN],dist[MAXN];
bool pos[MAXN],mark[MAXN];
vector<int> cycle;
queue<int> bfsq;
vector<pair<int,int>> order;
vector<int> indicator;

void dfs(int node)
{
    pos[node]=true;
    for (int sled:adj[node])
    {
        if (!pos[sled]) dfs(sled);
    }
    topolosko.push_back(node);
}

int32_t main()
{
    cin>>n;int saved=0;
    for (int i=1;i<=n;i++) {string s1,s2;cin>>s1>>s2;edges.insert({s1,s2});}
    if (n%2==1) {cout<<-1<<endl;return 0;}
    for (pair<string,string> edge:edges)
    {
        if (edges.find({edge.second,edge.first})!=edges.end()) {saved++;continue;}
        kompresija.push_back(edge.first);kompresija.push_back(edge.second);
    }
    sort(kompresija.begin(),kompresija.end());kompresija.erase(unique(kompresija.begin(),kompresija.end()),kompresija.end());
    for (pair<string,string> edge:edges)
    {
        if (edges.find({edge.second,edge.first})!=edges.end()) continue;
        int u=lower_bound(kompresija.begin(),kompresija.end(),edge.first)-kompresija.begin()+1;
        int v=lower_bound(kompresija.begin(),kompresija.end(),edge.second)-kompresija.begin()+1;
        parent[u]=v;adj[v].push_back(u);
    }
    for (int node=1;node<=(int)kompresija.size();node++)
    {
        if (!pos[node]) dfs(node);
    }
    reverse(topolosko.begin(),topolosko.end());
    for (int i=0;i<(int)topolosko.size();i++) idx[topolosko[i]]=i;
    for (int node=1;node<=(int)kompresija.size();node++)
    {
        for (int sled:adj[node])
        {
            if (idx[node]>=idx[sled]) indicator.push_back(node);
        }
    }
    for (int node=1;node<=n;node++) dist[node]=INT_MAX;
    for (int node:indicator)
    {
        int start=node;int target=start;
        while (parent[start]!=target) {cycle.push_back(parent[start]);start=parent[start];}
        cycle.push_back(target);for (int cycnode:cycle) {dist[cycnode]=0;bfsq.push(cycnode);}
        while (!bfsq.empty())
        {
            int curr=bfsq.front();bfsq.pop();
            for (int sled:adj[curr])
            {
                if (dist[sled]!=INT_MAX) continue;
                dist[sled]=dist[node]+1;bfsq.push(sled);
                order.push_back({dist[sled],sled});
            }
        }
        sort(order.begin(),order.end());for (int cycnode:cycle) order.push_back({0,cycnode});
        for (int i=0;i<(int)order.size();i++)
        {
            int curr=order[i].second;
            if (!mark[curr] and !mark[parent[curr]]) saved++;
            mark[curr]=true;mark[parent[curr]]=true;
        }
        order.clear();cycle.clear();
    }
    cout<<n-saved<<endl;return 0;
}
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...
#Result Execution timeMemoryGrader output
Fetching results...