#include <bits/stdc++.h>
using namespace std;
typedef pair<long long, long long> P;
const long long MAX = 2000010;
const long long MOD = 1000000007;
long long fac[MAX], finv[MAX], inv[MAX];
void COMinit() {
  fac[0] = fac[1] = 1;
  finv[0] = finv[1] = 1;
  inv[1] = 1;
  for (int i = 2; i < MAX; i++) {
    fac[i] = fac[i - 1] * i % MOD;
    inv[i] = MOD - inv[MOD % i] * (MOD / i) % MOD;
    finv[i] = finv[i - 1] * inv[i] % MOD;
  }
}
long long COM(int n, int k) {
  if (n < k) return 0;
  if (n < 0 || k < 0) return 0;
  return fac[n] * (finv[k] * finv[n - k] % MOD) % MOD;
}
long long Euclid(long long a, long long b) {
  while (1) {
    if (a < b) {
      int c = a;
      a = b;
      b = c;
    }
    if (a % b == 0) {
      return b;
    } else {
      a = a % b;
    }
  }
}
int main() {
  COMinit();
  long long n;
  cin >> n;
  vector<P> a;
  vector<P> b;
  vector<P> a2;
  vector<P> b2;
  vector<P> c;
  vector<P> d;
  vector<P> e;
  long long pow[n + 1];
  for (int i = 0; i <= n; i++) {
    if (i == 0) {
      pow[i] = 1;
    } else {
      pow[i] = pow[i - 1] * 2 % MOD;
    }
  }
  for (int i = 0; i < n; i++) {
    long long A, B;
    cin >> A >> B;
    if (A > 0 && B > 0) {
      a2.push_back(P(A, B));
    }
    if (A == 0 && B > 0) {
      c.push_back(P(A, B));
    }
    if (A < 0 && B > 0) {
      b2.push_back(P(-A, B));
    }
    if (A > 0 && B == 0) {
      d.push_back(P(A, B));
    }
    if (A == 0 && B == 0) {
      e.push_back(P(A, B));
    }
    if (A < 0 && B == 0) {
      d.push_back(P(A, B));
    }
    if (A > 0 && B < 0) {
      b2.push_back(P(A, -B));
    }
    if (A == 0 && B < 0) {
      c.push_back(P(A, B));
    }
    if (A < 0 && B < 0) {
      a2.push_back(P(-A, -B));
    }
  }
  long long ans2 = COM(e.size(), 2) % MOD;
  ans2 = (ans2 + (e.size() * (n - e.size())) % MOD) % MOD;
  ans2 = (ans2 + (c.size() * d.size()) % MOD) % MOD;
  long long ans = 1;
  for (int i = 0; i < a2.size(); i++) {
    P p = a2[i];
    long long D = Euclid(p.first, p.second);
    a.push_back(P(p.first / D, p.second / D));
  }
  for (int i = 0; i < b2.size(); i++) {
    P p = b2[i];
    long long D = Euclid(p.first, p.second);
    b.push_back(P(p.second / D, p.first / D));
  }
  sort(a.begin(), a.end());
  sort(b.begin(), b.end());
  a.push_back(P(1000000000000000000, 1000000000000000000));
  b.push_back(P(1000000000000000001, 1000000000000000001));
  long long cnta = 0;
  long long cntb = 0;
  long long cntA = 0;
  long long cntB = 0;
  long long flg = 0;
  P mem;
  while (cnta < a.size() && cntb < b.size()) {
    if (a[cnta] < b[cntb] && flg == 0) {
      cnta++;
      if (cnta < a.size()) {
        ans = ans * 2 % MOD;
      }
    }
    if (a[cnta] > b[cntb] && flg == 0) {
      cntb++;
      if (cntb < b.size()) {
        ans = ans * 2 % MOD;
      }
    }
    if (a[cnta] == b[cntb] && flg == 0) {
      cntA = 1;
      cntB = 0;
      flg = 1;
      mem = a[cnta];
      cnta++;
    }
    if (a[cnta] == b[cntb] && flg != 0) {
      cntA++;
      cnta++;
    }
    if (a[cnta] != b[cntb] && flg != 0) {
      if (b[cntb] == mem) {
        cntB++;
        cntb++;
      } else {
        flg = 0;
        long long k = pow[cntA];
        long long k2 = pow[cntB];
        ans = (ans * (k + k2 - 1)) % MOD;
      }
    }
  }
  long long k = pow[c.size()];
  long long k2 = pow[d.size()];
  ans = ans * (k + k2 - 1) % MOD;
  ans = (ans - 1 + e.size()) % MOD;
  cout << ans << endl;
  return 0;
}
