Problem p02679 (C++)

Buggy submission (status: Runtime Error):
#include <bits/stdc++.h>
using namespace std;

typedef pair<long long, long long> pll;

long long A[200005];
long long B[200005];
long long C[200005];
long long D[200005];
long long pow2[200005];

const long long MOD = 1e9 + 7;

map<pll, long long> map1;

void insert1(long long a, long long b, int i) {
  if (b == 0 && a == 0) {
    a = b = 0;
  } else if (b == 0) {
    b = 0;
    a = 1;
  } else if (a == 0) {
    a = 0;
    b = 1;
  } else {
    long long temp = __gcd(abs(a), abs(b));
    a /= temp;
    b /= temp;
  }

  if (a < 0) {
    a = -a;
    b = -b;
  }

  C[i] = a;
  D[i] = b;

  pll indx = pll(a, b);
  // printf("%lld %lld inserted into map\n", a, b);
  if (map1.find(indx) == map1.end()) {
    map1[indx] = 1;
  } else {
    map1[indx]++;
  }
}

int main() {
  int N;
  scanf("%d", &N);

  pow2[0] = 1;
  for (int i = 1; i <= N; i++) {
    scanf("%lld%lld", &A[i], &B[i]);

    if (A[i] == 0 && B[i] == 0) {
      throw;
    }
    // if(abs(A[i]) == abs(B[i])){throw;}
    pow2[i] = 2 * pow2[i - 1] % MOD;
  }

  map1[pll(0, 0)] = 0;
  for (int i = 1; i <= N; i++) {
    insert1(A[i], B[i], i);
  }

  long long ans = 1;
  long long temp = map1[pll(0, 0)];
  for (int i = 1; i <= N; i++) {
    // printf("C[%d]=%lld D[%d]=%lld\n", i, C[i], i, D[i]);
    if (C[i] == 0 && D[i] == 0) {
      continue;
    }

    // printf("%lld\n", map1[pll(C[i], D[i])]);

    long long ways = pow2[map1[pll(C[i], D[i])]];

    pll inv;
    if (C[i] == 0 || D[i] == 0) {
      // ways = pow2[map1[pll(C[i], D[i])]];
      map1[pll(C[i], D[i])] = 0;
      inv = pll(D[i], C[i]);
      if (map1.find(inv) != map1.end()) {
        ways += pow2[map1[inv]];
        map1[inv] = 0;
      } else {
        ways++;
      }
      ways = (ways + MOD - 1) % MOD;
      // throw;
    } else {
      map1[pll(C[i], D[i])] = 0;
      inv = pll(-D[i], C[i]);
      if (map1.find(inv) != map1.end()) {
        ways += pow2[map1[inv]];
        map1[inv] = 0;
      } else {
        ways++;
      }

      inv = pll(D[i], -C[i]);
      if (map1.find(inv) != map1.end()) {
        ways += pow2[map1[inv]];
        map1[inv] = 0;
      } else {
        ways++;
      }

      ways = (ways + MOD - 2) % MOD;
    }
    // printf("ways=%lld\n", ways);
    ans = ans * ways % MOD;
  }
  ans += temp;
  ans = (ans + MOD - 1) % MOD;

  printf("%lld", ans);
  return 0;
}


Fixed submission:
#include <bits/stdc++.h>
using namespace std;

typedef pair<long long, long long> pll;

long long A[200005];
long long B[200005];
long long C[200005];
long long D[200005];
long long pow2[200005];

const long long MOD = 1e9 + 7;

map<pll, long long> map1;

void insert1(long long a, long long b, int i) {
  if (b == 0 && a == 0) {
    a = b = 0;
  } else if (b == 0) {
    b = 0;
    a = 1;
  } else if (a == 0) {
    a = 0;
    b = 1;
  } else {
    long long temp = __gcd(abs(a), abs(b));
    a /= temp;
    b /= temp;
  }

  if (a < 0) {
    a = -a;
    b = -b;
  }

  C[i] = a;
  D[i] = b;

  pll indx = pll(a, b);
  // printf("%lld %lld inserted into map\n", a, b);
  if (map1.find(indx) == map1.end()) {
    map1[indx] = 1;
  } else {
    map1[indx]++;
  }
}

int main() {
  int N;
  scanf("%d", &N);

  pow2[0] = 1;
  for (int i = 1; i <= N; i++) {
    scanf("%lld%lld", &A[i], &B[i]);

    // if(A[i] == 0 && B[i] == 0){throw;}
    // if(abs(A[i]) == abs(B[i])){throw;}
    pow2[i] = 2 * pow2[i - 1] % MOD;
  }

  map1[pll(0, 0)] = 0;
  for (int i = 1; i <= N; i++) {
    insert1(A[i], B[i], i);
  }

  long long ans = 1;
  long long temp = map1[pll(0, 0)];
  for (int i = 1; i <= N; i++) {
    // printf("C[%d]=%lld D[%d]=%lld\n", i, C[i], i, D[i]);
    if (C[i] == 0 && D[i] == 0) {
      continue;
    }

    // printf("%lld\n", map1[pll(C[i], D[i])]);

    long long ways = pow2[map1[pll(C[i], D[i])]];

    pll inv;
    if (C[i] == 0 || D[i] == 0) {
      // ways = pow2[map1[pll(C[i], D[i])]];
      map1[pll(C[i], D[i])] = 0;
      inv = pll(D[i], C[i]);
      if (map1.find(inv) != map1.end()) {
        ways += pow2[map1[inv]];
        map1[inv] = 0;
      } else {
        ways++;
      }
      ways = (ways + MOD - 1) % MOD;
      // throw;
    } else {
      map1[pll(C[i], D[i])] = 0;
      inv = pll(-D[i], C[i]);
      if (map1.find(inv) != map1.end()) {
        ways += pow2[map1[inv]];
        map1[inv] = 0;
      } else {
        ways++;
      }

      inv = pll(D[i], -C[i]);
      if (map1.find(inv) != map1.end()) {
        ways += pow2[map1[inv]];
        map1[inv] = 0;
      } else {
        ways++;
      }

      ways = (ways + MOD - 2) % MOD;
    }
    // printf("ways=%lld\n", ways);
    ans = ans * ways % MOD;
  }
  ans += temp;
  ans = (ans + MOD - 1) % MOD;

  printf("%lld", ans);
  return 0;
}