Problem p01128 (C++) — buggy submission, verdict: Runtime Error

#include <algorithm>
#include <bitset>
#include <cassert>
#include <cctype>
#include <complex>
#include <cstdio>
#include <functional>
#include <iomanip>
#include <iostream>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <string>
#include <utility>
#include <vector>
using namespace std;

// common
#define BR "\\n"

#define ALL(c) (c).begin(), (c).end()
#define REP(i, n) for (int i = 0; i < (int)(n); ++i)
#define EACH(it, o) for (auto it = (o).begin(); it != (o).end(); ++it)
#define IN(l, v, r) ((l) <= (v) && (v) < (r))

typedef vector<int> vi;
typedef pair<int, int> pii;
typedef vector<pair<int, int>> vpii;
typedef long long ll;
typedef vector<long long> vl;
typedef pair<long long, long long> pll;
typedef vector<pair<long long, long long>> vpll;
typedef vector<string> vs;
typedef long double ld;

// debug
#ifdef NDEBUG
#define DUMP(x)
#define DUMPLN(x)
#define DEBUG(x)
#define DEBUGLN(x)
#define LINE()
#define LINELN()
#define CHECK(exp, act)
#define STOP(e)
#else
#define DUMP(x) cerr << #x << " = " << (x) << " "
#define DUMPLN(x) DUMP(x) << endl
#define DEBUG(x) DUMP(x) << LINE() << " " << __FILE__
#define DEBUGLN(x) DEBUG(x) << endl
#define LINE() cerr << " (L" << __LINE__ << ")"
#define LINELN() LINE() << endl
#define CHECK(exp, act)                                                        \\
  if (exp != act) {                                                            \\
    DUMPLN(exp);                                                               \\
    DEBUGLN(act);                                                              \\
  }
#define STOP(e)                                                                \\
  CHECK(e, true);                                                              \\
  if (!(e))                                                                    \\
    exit(1);
#endif

template <class T> inline string toString(const vector<T> &x) {
  stringstream ss;
  REP(i, x.size()) {
    if (i != 0)
      ss << " ";
    ss << x[i];
  }
  return ss.str();
}
template <class T> inline string toString(const vector<vector<T>> &map) {
  stringstream ss;
  REP(i, map.size()) {
    if (i != 0)
      ss << BR;
    ss << toString(map[i]);
  }
  return ss.str();
}
template <class K, class V> string toString(map<K, V> &x) {
  string res;
  stringstream ss;
  for (auto &p : x)
    ss << p.first << ":" << p.second << " ";
  return ss.str();
}

template <typename T, typename V> inline T mod(T v, V MOD) {
  return (v % MOD + MOD) % MOD;
}

int INF = 1 << 28;

namespace geo {
const double EPS = 1e-9;
typedef double PT;
typedef complex<PT> P;
typedef P vecP;
typedef vector<P> Polygon;

template <typename T> bool LT(T a, T b) { return a + EPS < b; }
template <typename T> bool GT(T a, T b) { return LT(b, a); }
template <typename T> bool EQ(T a, T b) { return !LT(a, b) && !GT(a, b); }

namespace VU {
static PT x(const vecP &a) { return real(a); }
static PT y(const vecP &a) { return imag(a); }

// ベクタの長さ
static PT length(const vecP &a) { return abs(a); }
// 単位ベクトル
static vecP unit_vector(const vecP &a) { return a / abs(a); }
// 法線ベクトル
static pair<vecP, vecP> normal_vector(const vecP &a) {
  return make_pair(a * vecP(0, 1), a * vecP(0, -1));
}
// 内積 (dot product) : a・b = |a||b|cosΘ
PT dot(const vecP &a, const vecP &b) { return x(conj(a) * b); }
// 外積 (cross product) : |a×b| = |a||b|sinΘ
PT cross(const vecP &a, const vecP &b) { return y(conj(a) * b); }
// 点aと点bの距離
static PT dist(const P &a, const P &b) { return abs(a - b); }

// 点の進行方向
int ccw(P a, P b, P c) {
  b -= a;
  c -= a;
  if (LT(cross(b, c), 0.0))
    return +1; // counter clockwise
  if (GT(cross(b, c), 0.0))
    return -1; // clockwise
  if (EQ(dot(b, c), 0.0))
    return +2; // c -- a -- b
  if (norm(b) < norm(c))
    return -2; // a -- b -- c
  return 0;
}

} // namespace VU
using namespace VU;
}; // namespace geo
using namespace geo;
namespace std {
bool operator<(const P &lhs, const P &rhs) {
  if (x(lhs) == x(rhs))
    return y(lhs) < y(rhs);
  return x(lhs) < x(rhs);
}
} // namespace std

namespace geo {
struct L {
  P p1, p2;
  L(P p1, P p2) : p1(p1), p2(p2) {}
  vecP vec() { return p2 - p1; }
  // 点との距離
  double line_dist(const P &b) {
    return abs(cross(vec(), b - p1)) / abs(vec());
  }
  double linesegment_dist(const P &b) {
    if (EQ(dot(p2 - p1, b - p1), 0.0))
      return abs(b - p1);
    if (EQ(dot(p1 - p2, b - p2), 0.0))
      return abs(b - p2);
    return line_dist(b);
  }
  double linesegment_dist(L &b) {
    if (is_intersected(b))
      return 0;
    return min(min(linesegment_dist(b.p1), linesegment_dist(b.p2)),
               min(b.linesegment_dist(p1), b.linesegment_dist(p2)));
  }

  // 線分同士の交差判定
  bool is_intersected(L &b) {
    if (LT(max(x(p1), x(p2)), min(x(b.p1), x(b.p2))))
      return false;
    if (LT(max(x(b.p1), x(b.p2)), min(x(p1), x(p2))))
      return false;
    if (LT(max(y(p1), y(p2)), min(y(b.p1), y(b.p2))))
      return false;
    if (LT(max(y(b.p1), y(b.p2)), min(y(p1), y(p2))))
      return false;
    return cross(vec(), b.p1 - p1) * cross(vec(), b.p2 - p1) < EPS &&
           cross(b.vec(), p1 - b.p1) * cross(b.vec(), p2 - b.p1) < EPS;
  }

  bool is_intersected_line(L &b) { return !is_parallel(b); }

  P intersection_point(L &b) {
    if (EQ(p1, b.p1) || EQ(p1, b.p2))
      return p1;
    if (EQ(p2, b.p1) || EQ(p2, b.p2))
      return p2;
    return p1 + vec() * cross(b.vec(), b.p1 - p1) / cross(b.vec(), vec());
  }
  P intersection_ls(L &b) {
    double d1 = abs(cross(b.vec(), p1 - b.p1));
    double d2 = abs(cross(b.vec(), p2 - b.p1));
    if (d1 + d2 == 0)
      return P(INF, INF);
    double t = d1 / (d1 + d2);
    return p1 + (p2 - p1) * t;
  }
  // 2直線の直交判定 : a⊥b <=> dot(a, b) = 0
  // みけんしょう
  bool is_orthogonal(L &b) { return EQ(dot(vec(), b.vec()), 0.0); }
  // 2直線の平行判定 : a//b <=> cross(a, b) = 0
  bool is_parallel(L &b) { return EQ(cross(vec(), b.vec()), 0.0); }

  // 直線と点の最短距離を実現する直線の点(すいせんの足)(みけんしょう)
  P nearest_point_line(P b) {
    return p1 + vec() * dot(vec(), b - p1) / norm(vec());
  }
  // 線分と点の最短距離を実現する線分嬢の点(みけんしょう)
  P nearest_point_linesegment(P b) {
    if (EQ(dot(vec(), b - p1), 0.0))
      return p1;
    if (EQ(dot(vec(), b - p2), 0.0))
      return p2;
    return nearest_point_line(b);
  }
};
} // namespace geo

int main() {
  int C;
  cin >> C;
  while (C-- != 0) {
    int xa, ya, xb, yb;
    cin >> xa >> ya >> xb >> yb;
    L base(P(xa, ya), P(xb, yb));
    int n;
    cin >> n;
    vector<pair<pair<P, int>, int>> inps;
    REP(i, n) {
      int xs, ys, xt, yt, o, l;
      cin >> xs >> ys >> xt >> yt >> o >> l;
      L line = L(P(xs, ys), P(xt, yt));
      if (base.is_intersected(line))
        inps.push_back(make_pair(make_pair(base.intersection_ls(line), o), l));
    }
    sort(ALL(inps));

    int res = 0;
    if (inps.size() > 0) {
      int prev = -1;
      {
        int o = inps[0].first.second, l = inps[0].second;
        if (o)
          prev = l;
        else
          prev = !l;
      }
      for (int i = 1; i < inps.size(); i++) {
        int o = inps[i].first.second, l = inps[i].second;
        if (o) {
          if (prev != l)
            res++;
          prev = l;
        } else {
          if (prev != !l)
            res++;
          prev = !l;
        }
      }
    }
    cout << res << endl;
  }
  return 0;
}

Error: 0

Fixed submission:

#include <algorithm>
#include <bitset>
#include <cassert>
#include <cctype>
#include <complex>
#include <cstdio>
#include <functional>
#include <iomanip>
#include <iostream>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <sstream>
#include <stack>
#include <string>
#include <utility>
#include <vector>
using namespace std;

// common
#define BR "\\n"

#define ALL(c) (c).begin(), (c).end()
#define REP(i, n) for (int i = 0; i < (int)(n); ++i)
#define EACH(it, o) for (auto it = (o).begin(); it != (o).end(); ++it)
#define IN(l, v, r) ((l) <= (v) && (v) < (r))

typedef vector<int> vi;
typedef pair<int, int> pii;
typedef vector<pair<int, int>> vpii;
typedef long long ll;
typedef vector<long long> vl;
typedef pair<long long, long long> pll;
typedef vector<pair<long long, long long>> vpll;
typedef vector<string> vs;
typedef long double ld;

// debug
#ifdef NDEBUG
#define DUMP(x)
#define DUMPLN(x)
#define DEBUG(x)
#define DEBUGLN(x)
#define LINE()
#define LINELN()
#define CHECK(exp, act)
#define STOP(e)
#else
#define DUMP(x) cerr << #x << " = " << (x) << " "
#define DUMPLN(x) DUMP(x) << endl
#define DEBUG(x) DUMP(x) << LINE() << " " << __FILE__
#define DEBUGLN(x) DEBUG(x) << endl
#define LINE() cerr << " (L" << __LINE__ << ")"
#define LINELN() LINE() << endl
#define CHECK(exp, act)                                                        \\
  if (exp != act) {                                                            \\
    DUMPLN(exp);                                                               \\
    DEBUGLN(act);                                                              \\
  }
#define STOP(e)                                                                \\
  CHECK(e, true);                                                              \\
  if (!(e))                                                                    \\
    exit(1);
#endif

template <class T> inline string toString(const vector<T> &x) {
  stringstream ss;
  REP(i, x.size()) {
    if (i != 0)
      ss << " ";
    ss << x[i];
  }
  return ss.str();
}
template <class T> inline string toString(const vector<vector<T>> &map) {
  stringstream ss;
  REP(i, map.size()) {
    if (i != 0)
      ss << BR;
    ss << toString(map[i]);
  }
  return ss.str();
}
template <class K, class V> string toString(map<K, V> &x) {
  string res;
  stringstream ss;
  for (auto &p : x)
    ss << p.first << ":" << p.second << " ";
  return ss.str();
}

template <typename T, typename V> inline T mod(T v, V MOD) {
  return (v % MOD + MOD) % MOD;
}

int INF = 1 << 28;

namespace geo {
const double EPS = 1e-9;
typedef double PT;
typedef complex<PT> P;
typedef P vecP;
typedef vector<P> Polygon;

template <typename T> bool LT(T a, T b) { return a + EPS < b; }
template <typename T> bool GT(T a, T b) { return LT(b, a); }
template <typename T> bool EQ(T a, T b) { return !LT(a, b) && !GT(a, b); }

namespace VU {
static PT x(const vecP &a) { return real(a); }
static PT y(const vecP &a) { return imag(a); }

// ベクタの長さ
static PT length(const vecP &a) { return abs(a); }
// 単位ベクトル
static vecP unit_vector(const vecP &a) { return a / abs(a); }
// 法線ベクトル
static pair<vecP, vecP> normal_vector(const vecP &a) {
  return make_pair(a * vecP(0, 1), a * vecP(0, -1));
}
// 内積 (dot product) : a・b = |a||b|cosΘ
PT dot(const vecP &a, const vecP &b) { return x(conj(a) * b); }
// 外積 (cross product) : |a×b| = |a||b|sinΘ
PT cross(const vecP &a, const vecP &b) { return y(conj(a) * b); }
// 点aと点bの距離
static PT dist(const P &a, const P &b) { return abs(a - b); }

// 点の進行方向
int ccw(P a, P b, P c) {
  b -= a;
  c -= a;
  if (LT(cross(b, c), 0.0))
    return +1; // counter clockwise
  if (GT(cross(b, c), 0.0))
    return -1; // clockwise
  if (EQ(dot(b, c), 0.0))
    return +2; // c -- a -- b
  if (norm(b) < norm(c))
    return -2; // a -- b -- c
  return 0;
}

} // namespace VU
using namespace VU;
}; // namespace geo
using namespace geo;
namespace std {
bool operator<(const P &lhs, const P &rhs) {
  if (x(lhs) == x(rhs))
    return y(lhs) < y(rhs);
  return x(lhs) < x(rhs);
}
} // namespace std

namespace geo {
struct L {
  P p1, p2;
  L(P p1, P p2) : p1(p1), p2(p2) {}
  vecP vec() { return p2 - p1; }
  // 点との距離
  double line_dist(const P &b) {
    return abs(cross(vec(), b - p1)) / abs(vec());
  }
  double linesegment_dist(const P &b) {
    if (EQ(dot(p2 - p1, b - p1), 0.0))
      return abs(b - p1);
    if (EQ(dot(p1 - p2, b - p2), 0.0))
      return abs(b - p2);
    return line_dist(b);
  }
  double linesegment_dist(L &b) {
    if (is_intersected(b))
      return 0;
    return min(min(linesegment_dist(b.p1), linesegment_dist(b.p2)),
               min(b.linesegment_dist(p1), b.linesegment_dist(p2)));
  }

  // 線分同士の交差判定
  bool is_intersected(L &b) {
    if (LT(max(x(p1), x(p2)), min(x(b.p1), x(b.p2))))
      return false;
    if (LT(max(x(b.p1), x(b.p2)), min(x(p1), x(p2))))
      return false;
    if (LT(max(y(p1), y(p2)), min(y(b.p1), y(b.p2))))
      return false;
    if (LT(max(y(b.p1), y(b.p2)), min(y(p1), y(p2))))
      return false;
    return cross(vec(), b.p1 - p1) * cross(vec(), b.p2 - p1) < EPS &&
           cross(b.vec(), p1 - b.p1) * cross(b.vec(), p2 - b.p1) < EPS;
  }

  bool is_intersected_line(L &b) { return !is_parallel(b); }

  P intersection_point(L &b) {
    if (EQ(p1, b.p1) || EQ(p1, b.p2))
      return p1;
    if (EQ(p2, b.p1) || EQ(p2, b.p2))
      return p2;
    return p1 + vec() * cross(b.vec(), b.p1 - p1) / cross(b.vec(), vec());
  }
  P intersection_ls(L &b) {
    double d1 = abs(cross(b.vec(), p1 - b.p1));
    double d2 = abs(cross(b.vec(), p2 - b.p1));
    if (d1 + d2 == 0)
      return P(INF, INF);
    double t = d1 / (d1 + d2);
    return p1 + (p2 - p1) * t;
  }
  // 2直線の直交判定 : a⊥b <=> dot(a, b) = 0
  // みけんしょう
  bool is_orthogonal(L &b) { return EQ(dot(vec(), b.vec()), 0.0); }
  // 2直線の平行判定 : a//b <=> cross(a, b) = 0
  bool is_parallel(L &b) { return EQ(cross(vec(), b.vec()), 0.0); }

  // 直線と点の最短距離を実現する直線の点(すいせんの足)(みけんしょう)
  P nearest_point_line(P b) {
    return p1 + vec() * dot(vec(), b - p1) / norm(vec());
  }
  // 線分と点の最短距離を実現する線分嬢の点(みけんしょう)
  P nearest_point_linesegment(P b) {
    if (EQ(dot(vec(), b - p1), 0.0))
      return p1;
    if (EQ(dot(vec(), b - p2), 0.0))
      return p2;
    return nearest_point_line(b);
  }
};
} // namespace geo

int main() {
  int C;
  cin >> C;
  while (C-- != 0) {
    int xa, ya, xb, yb;
    cin >> xa >> ya >> xb >> yb;
    L base(P(xa, ya), P(xb, yb));
    int n;
    cin >> n;
    vector<pair<pair<P, int>, int>> inps;
    REP(i, n) {
      int xs, ys, xt, yt, o, l;
      cin >> xs >> ys >> xt >> yt >> o >> l;
      L line = L(P(xs, ys), P(xt, yt));
      if (base.is_intersected(line))
        inps.push_back(make_pair(make_pair(base.intersection_ls(line), o), l));
    }
    sort(ALL(inps));
    int prev = -1;
    {
      int o = inps[0].first.second, l = inps[0].second;
      if (o)
        prev = l;
      else
        prev = !l;
    }
    int res = 0;
    for (int i = 1; i < inps.size(); i++) {
      int o = inps[i].first.second, l = inps[i].second;
      if (o) {
        if (prev != l)
          res++;
        prev = l;
      } else {
        if (prev != !l)
          res++;
        prev = !l;
      }
    }
    cout << res << endl;
  }
  return 0;
}