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

#include <bits/stdc++.h>

#define REP(i, s, n) for (int i = s; i < n; i++)
#define rep(i, n) REP(i, 0, n)
#define EPS (1e-8)
#define equals(a, b) (fabs((a) - (b)) < EPS)
#define COUNTER_CLOCKWISE 1
#define CLOCKWISE -1
#define ONLINE_BACK 2
#define ONLINE_FRONT -2
#define ON_SEGMENT 0

using namespace std;

class Point {
public:
  double x, y;

  Point(double x = 0, double y = 0) : x(x), y(y) {}

  Point operator+(Point p) { return Point(x + p.x, y + p.y); }
  Point operator-(Point p) { return Point(x - p.x, y - p.y); }
  Point operator*(double a) { return Point(a * x, a * y); }
  Point operator/(double a) { return Point(x / a, y / a); }
  Point operator*(Point a) {
    return Point(x * a.x - y * a.y, x * a.y + y * a.x);
  }

  bool operator<(const Point &p) const {
    return !equals(x, p.x) ? x < p.x : (!equals(y, p.y) && y < p.y);
  }

  bool operator==(const Point &p) const {
    return fabs(x - p.x) < EPS && fabs(y - p.y) < EPS;
  }
};

struct Segment {
  Point p1, p2;
  Segment(Point p1 = Point(), Point p2 = Point()) : p1(p1), p2(p2) {}
  bool operator<(const Segment &s) const {
    return (p2 == s.p2) ? p1 < s.p1 : p2 < s.p2;
  }
  bool operator==(const Segment &s) const {
    return (s.p1 == p1 && s.p2 == p2) || (s.p1 == p2 && s.p2 == p1);
  }
};

typedef Point Vector;
typedef Segment Line;
typedef vector<Point> Polygon;

ostream &operator<<(ostream &os, const Point &a) {
  os << "(" << a.x << "," << a.y << ")";
}

ostream &operator<<(ostream &os, const Segment &a) {
  os << "( " << a.p1 << " , " << a.p2 << " )";
}

double dot(Point a, Point b) { return a.x * b.x + a.y * b.y; }

double cross(Point a, Point b) { return a.x * b.y - a.y * b.x; }

double norm(Point a) { return a.x * a.x + a.y * a.y; }

double abs(Point a) { return sqrt(norm(a)); }

// rad は角度をラジアンで持たせること
Point rotate(Point a, double rad) {
  return Point(cos(rad) * a.x - sin(rad) * a.y,
               sin(rad) * a.x + cos(rad) * a.y);
}

// 度をラジアンに変換
double toRad(double agl) { return agl * M_PI / 180.0; }

// a => prev, b => cur, c=> next
// prev から cur へ行って next へ行く際の角度を求める
double getArg(Point a, Point b, Point c) {
  double arg1 = atan2(b.y - a.y, b.x - a.x);
  double arg2 = atan2(c.y - b.y, c.x - b.x);
  double arg = fabs(arg1 - arg2);
  while (arg > M_PI)
    arg -= 2.0 * M_PI;
  return fabs(arg);
}

int ccw(Point p0, Point p1, Point p2) {
  Point a = p1 - p0;
  Point b = p2 - p0;
  if (cross(a, b) > EPS)
    return COUNTER_CLOCKWISE;
  if (cross(a, b) < -EPS)
    return CLOCKWISE;
  if (dot(a, b) < -EPS)
    return ONLINE_BACK;
  if (norm(a) < norm(b))
    return ONLINE_FRONT;
  return ON_SEGMENT;
}

bool intersectSS(Line s, Line t) {
  return ccw(s.p1, s.p2, t.p1) * ccw(s.p1, s.p2, t.p2) <= 0 &&
         ccw(t.p1, t.p2, s.p1) * ccw(t.p1, t.p2, s.p2) <= 0;
}

// cross product of pq and pr
double cross3p(Point p, Point q, Point r) {
  return (r.x - q.x) * (p.y - q.y) - (r.y - q.y) * (p.x - q.x);
}

// returns true if point r is on the same line as the line pq
bool collinear(Point p, Point q, Point r) {
  return fabs(cross3p(p, q, r)) < EPS;
}

// returns true if point t is on the left side of line pq
bool ccwtest(Point p, Point q, Point r) {
  return cross3p(p, q, r) > 0; // can be modified to accept collinear points
}

bool onSegment(Point p, Point q, Point r) {
  return collinear(p, q, r) &&
         equals(sqrt(pow(p.x - r.x, 2) + pow(p.y - r.y, 2)) +
                    sqrt(pow(r.x - q.x, 2) + pow(r.y - q.y, 2)),
                sqrt(pow(p.x - q.x, 2) + pow(p.y - q.y, 2)));
}

int par[1100];

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

void unit(int x, int y) {
  x = find(x), y = find(y);
  if (x != y)
    par[x] = y;
}

vector<vector<int>> connect_counter;
int connect[10][6] = {{+2, +2, +2, +2, -1, -1}, {+0, -1, -1, -1, -1, -1},
                      {+1, +1, +2, +2, +2, -1}, {+1, +1, +1, +3, -1, -1},
                      {+1, +1, +2, -1, -1, -1}, {+1, +1, +2, +2, +2, -1},
                      {+1, +2, +2, +2, +3, -1}, {+1, +1, +2, +3, -1, -1},
                      {+2, +2, +2, +3, +3, -1}, {+2, +2, +2, +2, -1, -1}};

int WhatIsThis(vector<Segment> &segs) {
  if (segs.size() == 1)
    return 1;
  vector<int> tmp;
  Segment cur, next;
  rep(i, segs.size()) {
    int cnt = 0;
    Segment touch;
    rep(j, segs.size()) if (i != j) if (intersectSS(segs[i], segs[j])) {
      ++cnt;
      touch = segs[j];
    }
    if (cnt == 1) {
      cur = segs[i], next = touch;
    }
    assert(cnt);
    tmp.push_back(cnt);
  }
  sort(tmp.begin(), tmp.end());
  if (tmp == connect_counter[3])
    return 3;
  if (tmp == connect_counter[6])
    return 6;
  if (tmp == connect_counter[8])
    return 8;
  if (tmp == connect_counter[2]) {
    Point p0, p1, p2;
    if (cur.p1 == next.p1)
      p0 = cur.p2, p1 = cur.p1, p2 = next.p2;
    if (cur.p1 == next.p2)
      p0 = cur.p2, p1 = cur.p1, p2 = next.p1;
    if (cur.p2 == next.p1)
      p0 = cur.p1, p1 = cur.p2, p2 = next.p2;
    if (cur.p2 == next.p2)
      p0 = cur.p1, p1 = cur.p2, p2 = next.p1;
    if (ccw(p0, p1, p2) == CLOCKWISE)
      return 2;
    else
      return 5;
  }
  bool hasMiddle = false;
  rep(i, segs.size())
      rep(j, segs.size()) if (i != j && intersectSS(segs[i], segs[j])) {
    if (segs[i].p1 == segs[j].p1 || segs[i].p1 == segs[j].p2 ||
        segs[i].p2 == segs[j].p1 || segs[i].p2 == segs[j].p2)
      continue;
    hasMiddle = true;
    goto Skip;
  }
Skip:;
  if (tmp == connect_counter[4])
    return (hasMiddle ? 4 : 7);
  if (tmp == connect_counter[0])
    return (hasMiddle ? 9 : 0);
  return -1;
}

void compute(int n, vector<Segment> &segs) {
  vector<int> counter(10, 0);

  rep(i, n) par[i] = i;
  rep(i, n) REP(j, i + 1, n) if (intersectSS(segs[i], segs[j])) unit(i, j);
  int dex = 0;
  map<int, int> S;
  rep(i, n) if (!S.count(find(i))) S[find(i)] = dex++;
  int V = S.size();
  vector<vector<Segment>> buf(V, vector<Segment>());
  rep(i, n) buf[S[find(i)]].push_back(segs[i]);

  rep(i, V) {
    int result = WhatIsThis(buf[i]);
    ++counter[result];
  }

  rep(i, 10) {
    if (i)
      printf(" ");
    printf("%d", counter[i]);
  }
  puts("");
}

int main() {
  connect_counter.clear();
  connect_counter.resize(10, vector<int>());
  rep(i, 10) rep(j, 6) if (connect[i][j] != -1) connect_counter[i].push_back(
      connect[i][j]);

  int n;
  while (cin >> n, n) {
    vector<Segment> segs(n);
    rep(i, n) cin >> segs[i].p1.x >> segs[i].p1.y >> segs[i].p2.x >>
        segs[i].p2.y;
    compute(n, segs);
  }
  return 0;
}

Error: -11

Fixed submission:

#include <algorithm>
#include <climits>
#include <cstdio>
#include <iostream>
#include <set>
#include <vector>

#define REP(i, s, n) for (int i = s; i < n; i++)
#define rep(i, n) REP(i, 0, n)
#define IINF (INT_MAX)
#define MAX_E 13

using namespace std;

int n, m;
string e[MAX_E];
string text;
bool dp[5001][(1 << 12)];

int main() {
  while (scanf("%d %d", &n, &m), n | m) {
    rep(i, n) { cin >> e[i]; }
    text = "";
    rep(i, m) {
      string content;
      cin >> content;
      text += content;
    }

    int len = text.size();
    rep(i, len + 1) rep(j, (1 << n)) dp[i][j] = false;
    int ans = 0;

    rep(i, len) {
      rep(j, n) {
        int e_len = e[j].size();
        if (i + e_len > text.size())
          continue;
        if (text[i] != e[j][0])
          continue;
        if (text.substr(i, e_len) == e[j]) {
          dp[i + e_len][(1 << j)] = true;
        }
      }
    }

    rep(cur, len + 1) {
      rep(state, (1 << n)) {
        if (dp[cur][state] == false)
          continue;
        rep(k, n) {
          if ((state >> k) & 1)
            continue;
          int e_len = e[k].size();
          if (e[k][0] != text[cur])
            continue;
          if (text.size() < cur + e_len)
            continue;
          if (text.substr(cur, e_len) == e[k]) {
            dp[cur + e_len][state | (1 << k)] = true;
          }
        }
      }
      if (dp[cur][(1 << n) - 1])
        ans++;
    }
    printf("%d\\n", ans);
  }
  return 0;
}