#include <bits/stdc++.h>
using namespace std;
using UL = unsigned int;
using ULL = unsigned long long;
using LL = long long;
ULL GCD(ULL a, ULL b) { return b ? GCD(b, a % b) : a; }
struct Problem {
  UL N;
  pair<LL, LL> A[200000];
  map<pair<LL, LL>, UL> Q;
  static const ULL M = 1000000007;
  ULL P[200001];
  ULL iP[200001];
  pair<LL, LL> inv(pair<LL, LL> a) {
    swap(a.first, a.second);
    if (a.first < 0)
      a.first *= -1;
    else
      a.second *= -1;
    return a;
  }
  void Solve() {
    scanf("%d", &N);
    for (UL i = 0; i < (N); i++) {
      scanf("%lld%lld", &A[i].first, &A[i].second);
      if (A[i].first == 0)
        A[i].second /= abs(A[i].second);
      else if (A[i].second == 0)
        A[i].first /= abs(A[i].first);
      else {
        LL g = GCD(abs(A[i].first), abs(A[i].second));
        A[i].first /= g;
        A[i].second /= g;
        if (A[i].first < 0) {
          A[i].first *= -1;
          A[i].second *= -1;
        }
      }
      Q[A[i]]++;
    }
    ULL ans = 1;
    P[0] = 1;
    for (UL i = 1; i <= 200000; i++) P[i] = P[i - 1] * 2 % M;
    iP[0] = 1;
    for (UL i = 1; i <= 200000; i++) iP[i] = iP[i - 1] * 500000004 % M;
    for (auto& q : Q) {
      auto p = q.first;
      UL c = q.second;
      auto i = inv(p);
      ULL tmp = P[c] - 1;
      if (p < i)
        if (Q.find(i) != Q.end()) {
          tmp = tmp * iP[Q[i]] % M;
        }
      ans = (ans + ans * tmp) % M;
    }
    ans = (ans + M - 1) % M;
    printf("%lld\n", ans);
  }
};
int main() {
  unique_ptr<Problem> p(new Problem());
  p->Solve();
  return 0;
}
