Submission #55183

#TimeUsernameProblemLanguageResultExecution timeMemory
55183paulicaPrinted Circuit Board (CEOI12_circuit)C++14
75 / 100
786 ms16012 KiB
#include <bits/stdc++.h>
using namespace std;

#define _ << " _ " <<
#define TRACE(x) cout << #x << " = " << x << endl

#define fi first
#define se second
typedef pair<int, int> pii;
typedef long long ll;
typedef long double ld;

const int MaxN = 2e5 + 10;

int n, x[MaxN], y[MaxN];
pair<int, int> line[MaxN];

ll ccw(int i, int j, int k) {
    return (ll)x[i] * (y[j] - y[k]) +
           (ll)x[j] * (y[k] - y[i]) +
           (ll)x[k] * (y[i] - y[j]);
}

ll ccw0(int i, int j) {
    return (ll)x[i] * y[j] - (ll)x[j] * y[i];
}

ll dist(int i) {
    return (ll)x[i] * x[i] + (ll)y[i] * y[i];
}

bool equ(int i, int j) {
    return (ll)y[i] * x[j] == (ll)y[j] * x[i];
}

bool pointCmp(int i, int j) {
    if (equ(i, j)) return dist(i) < dist(j);
    return (ll)y[i] * x[j] < (ll)y[j] * x[i];
}

bool eventCmp(pair<pii, int>& a, pair<pii, int>& b) {
    if (equ(a.fi.fi, b.fi.fi) && a.se != b.se) return a.se < b.se;
    return pointCmp(a.fi.fi, b.fi.fi);
}

bool above(int i, int j) {
    int a = line[j].fi, b = line[j].se;

    if (ccw0(a, b) == 0) return x[i] >= max(x[a], x[b]);
    else if (i == a || i == b) return false;
    else return (ccw0(a, i) < 0) || (ccw(a, b, i) < 0) || (ccw0(i, b) < 0);
}

struct lineCmp {
    bool operator()(int i, int j) {
        if (i == j) return false;

        int a1 = line[i].fi, b1 = line[i].se;
        int a2 = line[j].fi, b2 = line[j].se;

        if (pointCmp(a1, a2) && pointCmp(a2, b1))
            return above(a2, i);
        else if (pointCmp(a1, b2) && pointCmp(b2, b1))
            return above(b2, i);
        else if (pointCmp(a2, a1) && pointCmp(a1, b2))
            return !above(a1, j);
        else if (pointCmp(a2, b1) && pointCmp(b1, b2))
            return !above(b1, j);
        else if (b1 == a2)
            return false;
        else if (b2 == a1)
           return true;
    }
};

int main() {
    ios_base::sync_with_stdio(false);
    cin.tie(0);

    cin >> n;

    vector<pair<pii, int>> events;

    for (int i = 0; i < n; i++) {
        cin >> x[i] >> y[i];
        events.push_back({{i, i}, 1});
    }
    
    for (int i = 0; i < n; i++) {
        if (i == n - 1) line[i] = {i, 0};
        else line[i] = {i, i + 1};
        
        if (pointCmp(line[i].se, line[i].fi))
            swap(line[i].fi, line[i].se);

        events.push_back({{line[i].fi, i}, 0});
        events.push_back({{line[i].se, i}, 2});
    }

    sort(events.begin(), events.end(), eventCmp);

    multiset<int, lineCmp> lines;

    vector<int> sol;

    for (auto ev : events) {
        if (ev.se == 0) {
            lines.insert(ev.fi.se);
        } else if (ev.se == 1) {
            int i = ev.fi.se;
            int j = *lines.begin();
            if (!above(i, j)) sol.push_back(i);
        } else {
            lines.erase(ev.fi.se);
        }
    }

    sort(sol.begin(), sol.end());

    cout << sol.size() << "\n";
    for (int i : sol) cout << i + 1 << " ";

    return 0;
}

Compilation message (stderr)

circuit.cpp: In member function 'bool lineCmp::operator()(int, int)':
circuit.cpp:73:5: warning: control reaches end of non-void function [-Wreturn-type]
     }
     ^
#Verdict Execution timeMemoryGrader output
Fetching results...