Problem p00877 (C++) — buggy submission, verdict: Time Limit Exceeded

#include "bits/stdc++.h"

using namespace std;
using ld = long double;
using Point = std::complex<ld>;
using P = pair<int, int>;

const ld eps = 1e-9, pi = acos(-1.0);

namespace std {
bool operator<(const Point &lhs, const Point &rhs) {
  if (lhs.real() < rhs.real() - eps)
    return true;
  if (lhs.real() > rhs.real() + eps)
    return false;
  return lhs.imag() < rhs.imag();
}
} // namespace std

Point input_point() {
  ld x, y;
  std::cin >> x >> y;
  return Point(x, y);
}

bool eq(ld a, ld b) { return (abs(a - b) < eps); }

ld dot(Point a, Point b) { return real(conj(a) * b); }

ld cross(Point a, Point b) { return imag(conj(a) * b); }

// CCW::counter clockwise
int ccw(Point a, Point b, Point c) {
  b -= a;
  c -= a;
  if (cross(b, c) > eps)
    return 2; // a,b,c : counter-clockwise
  if (cross(b, c) < -eps)
    return 0; // a,b,c : clockwise
  return 1;
}

class Line {
public:
  Point a, b;
  Line() : a(Point(0, 0)), b(Point(0, 0)) {}
  Line(Point a, Point b) : a(a), b(b) {}
};

ld dot(Line l, Line m) { return dot((l.a - l.b), (m.a - m.b)); }

// l, m が交点を持つか
bool isis_ll(Line l, Line m) { return !eq(cross(l.b - l.a, m.b - m.a), 0); }

// s : segment
bool isis_ls(Line l, Line s) {
  return isis_ll(l, s) &&
         (cross(l.b - l.a, s.a - l.a) * cross(l.b - l.a, s.b - l.a) < eps);
}

bool isis_ss(Line s, Line t) {
  return ccw(s.a, s.b, t.a) * ccw(s.a, s.b, t.b) <= 0 &&
         ccw(t.a, t.b, s.a) * ccw(t.a, t.b, s.b) <= 0;
}

// p が l 上に存在するか
bool isis_lp(Line l, Point p) { return (abs(cross(l.b - p, l.a - p)) < eps); }

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

  int n, m;
  while (cin >> n >> m, n || m) {
    vector<Point> bs(n), ws(m);
    for (int i = 0; i < n; i++) {
      bs[i] = input_point();
    }
    for (int i = 0; i < m; i++) {
      ws[i] = input_point();
    }
    if (n == 1 && m == 1) {
      cout << "YES" << endl;
      continue;
    }
    bool line = true;
    for (int i = 0; i < n; i++)
      if (!isis_lp(Line(bs[0], ws[0]), bs[i]))
        line = false;
    for (int i = 0; i < m; i++)
      if (!isis_lp(Line(bs[0], ws[0]), ws[i]))
        line = false;
    if (line) {
      vector<P> ps;
      for (int i = 0; i < n; i++)
        ps.push_back(P(bs[i].real(), 0));
      for (int i = 0; i < m; i++)
        ps.push_back(P(ws[i].real(), 1));
      sort(ps.begin(), ps.end());
      int cnt = 0;
      for (int i = 0; i < n + m; i++)
        if (ps[i].second != ps[i - 1].second)
          cnt++;
      cout << (cnt <= 1 ? "YES" : "NO") << endl;
      continue;
    }
    bool f = false;
    for (int i = 0; i < n; i++) {
      for (int j = i + 1; j < n; j++) {
        bool tmp = true;
        int bf = 0, wf = 0;
        for (int k = 0; k < n; k++) {
          bf |= (1 << ccw(bs[i], bs[j], bs[k]));
        }
        if ((bf & 4) && (bf & 1))
          continue;
        for (int k = 0; k < m; k++) {
          wf |= (1 << ccw(bs[i], bs[j], ws[k]));
        }
        if ((wf & 4) && (wf & 1))
          continue;
        for (int k = 0; k < 3; k++) {
          if (((bf >> k) & 1) & ((wf >> k) & 1))
            tmp = false;
        }
        if (tmp)
          f = true;
      }
    }
    for (int i = 0; i < m; i++) {
      for (int j = i + 1; j < m; j++) {
        bool tmp = true;
        int bf = 0, wf = 0;
        for (int k = 0; k < n; k++) {
          bf |= (1 << ccw(ws[i], ws[j], bs[k]));
        }
        if ((bf & 4) && (bf & 1))
          continue;
        for (int k = 0; k < m; k++) {
          wf |= (1 << ccw(ws[i], ws[j], ws[k]));
        }
        if ((wf & 4) && (wf & 1))
          continue;
        for (int k = 0; k < 3; k++) {
          if (((bf >> k) & 1) & ((wf >> k) & 1))
            tmp = false;
        }
        if (tmp)
          f = true;
      }
    }
    cout << (f ? "YES" : "NO") << '\\n';
  }
}


Error: TLE

Fixed submission:

#include "bits/stdc++.h"

using namespace std;
using ld = long double;
using Point = std::complex<ld>;
using P = pair<int, int>;

const ld eps = 1e-9, pi = acos(-1.0);

namespace std {
bool operator<(const Point &lhs, const Point &rhs) {
  if (lhs.real() < rhs.real() - eps)
    return true;
  if (lhs.real() > rhs.real() + eps)
    return false;
  return lhs.imag() < rhs.imag();
}
} // namespace std

Point input_point() {
  ld x, y;
  std::cin >> x >> y;
  return Point(x, y);
}

bool eq(ld a, ld b) { return (abs(a - b) < eps); }

ld dot(Point a, Point b) { return real(conj(a) * b); }

ld cross(Point a, Point b) { return imag(conj(a) * b); }

// CCW::counter clockwise
int ccw(Point a, Point b, Point c) {
  b -= a;
  c -= a;
  if (cross(b, c) > eps)
    return 2; // a,b,c : counter-clockwise
  if (cross(b, c) < -eps)
    return 0; // a,b,c : clockwise
  return 1;
}

class Line {
public:
  Point a, b;
  Line() : a(Point(0, 0)), b(Point(0, 0)) {}
  Line(Point a, Point b) : a(a), b(b) {}
};

ld dot(Line l, Line m) { return dot((l.a - l.b), (m.a - m.b)); }

// l, m が交点を持つか
bool isis_ll(Line l, Line m) { return !eq(cross(l.b - l.a, m.b - m.a), 0); }

// s : segment
bool isis_ls(Line l, Line s) {
  return isis_ll(l, s) &&
         (cross(l.b - l.a, s.a - l.a) * cross(l.b - l.a, s.b - l.a) < eps);
}

bool isis_ss(Line s, Line t) {
  return ccw(s.a, s.b, t.a) * ccw(s.a, s.b, t.b) <= 0 &&
         ccw(t.a, t.b, s.a) * ccw(t.a, t.b, s.b) <= 0;
}

// p が l 上に存在するか
bool isis_lp(Line l, Point p) { return (abs(cross(l.b - p, l.a - p)) < eps); }

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

  int n, m;
  while (cin >> n >> m, n || m) {
    vector<Point> bs(n), ws(m);
    for (int i = 0; i < n; i++) {
      bs[i] = input_point();
    }
    for (int i = 0; i < m; i++) {
      ws[i] = input_point();
    }
    if (n == 1 && m == 1) {
      cout << "YES" << endl;
      continue;
    }
    bool line = true;
    for (int i = 0; i < n; i++)
      if (!isis_lp(Line(bs[0], ws[0]), bs[i]))
        line = false;
    for (int i = 0; i < m; i++)
      if (!isis_lp(Line(bs[0], ws[0]), ws[i]))
        line = false;
    if (line) {
      vector<P> ps;
      for (int i = 0; i < n; i++)
        ps.push_back(P(bs[i].real(), 0));
      for (int i = 0; i < m; i++)
        ps.push_back(P(ws[i].real(), 1));
      sort(ps.begin(), ps.end());
      int cnt = 0;
      for (int i = 0; i < n + m; i++)
        if (ps[i].second != ps[i - 1].second)
          cnt++;
      cout << (cnt <= 1 ? "YES" : "NO") << endl;
      continue;
    }
    bool f = false;
    for (int i = 0; i < n; i++) {
      for (int j = i + 1; j < n; j++) {
        bool tmp = true;
        int bf = 0, wf = 0;
        for (int k = 0; k < n; k++) {
          bf |= (1 << ccw(bs[i], bs[j], bs[k]));
        }
        for (int k = 0; k < m; k++) {
          wf |= (1 << ccw(bs[i], bs[j], ws[k]));
        }
        for (int k = 0; k < 3; k++) {
          if (((bf >> k) & 1) & ((wf >> k) & 1))
            tmp = false;
        }
        if ((bf & 4) && (bf & 1))
          tmp = false;
        if ((wf & 4) && (wf & 1))
          tmp = false;
        if (tmp)
          f = true;
      }
    }
    for (int i = 0; i < m; i++) {
      for (int j = i + 1; j < m; j++) {
        bool tmp = true;
        int bf = 0, wf = 0;
        for (int k = 0; k < n; k++) {
          bf |= (1 << ccw(ws[i], ws[j], bs[k]));
        }
        for (int k = 0; k < m; k++) {
          wf |= (1 << ccw(ws[i], ws[j], ws[k]));
        }
        for (int k = 0; k < 3; k++) {
          if (((bf >> k) & 1) & ((wf >> k) & 1))
            tmp = false;
        }
        if ((bf & 4) && (bf & 1))
          tmp = false;
        if ((wf & 4) && (wf & 1))
          tmp = false;
        if (tmp)
          f = true;
      }
    }
    cout << (f ? "YES" : "NO") << endl;
  }
}