#include <bits/stdc++.h>
const double EPS = 1e-10;
using namespace std;
struct mint {
  long long x;
  mint(long long x = 0) : x((x % 1000000007 + 1000000007) % 1000000007) {}
  mint operator-() const { return mint(-x); }
  mint& operator+=(const mint a) {
    if ((x += a.x) >= 1000000007) x -= 1000000007;
    return *this;
  }
  mint& operator-=(const mint a) {
    if ((x += 1000000007 - a.x) >= 1000000007) x -= 1000000007;
    return *this;
  }
  mint& operator*=(const mint a) {
    (x *= a.x) %= 1000000007;
    return *this;
  }
  mint operator+(const mint a) const { return mint(*this) += a; }
  mint operator-(const mint a) const { return mint(*this) -= a; }
  mint operator*(const mint a) const { return mint(*this) *= a; }
  mint pow(long long t) const {
    if (!t) return 1;
    mint a = pow(t >> 1);
    a *= a;
    if (t & 1) a *= *this;
    return a;
  }
  mint inv() const { return pow(1000000007 - 2); }
  mint& operator/=(const mint a) { return *this *= a.inv(); }
  mint operator/(const mint a) const { return mint(*this) /= a; }
};
istream& operator>>(istream& is, const mint& a) { return is >> a.x; }
ostream& operator<<(ostream& os, const mint& a) { return os << a.x; }
template <typename T>
ostream& operator<<(ostream& os, const vector<T>& V) {
  long long N = V.size();
  for (long long i = 0; i < N - 1; i++) {
    os << V[i] << ' ';
  }
  os << V[N - 1];
  return os;
}
template <typename T>
ostream& operator<<(ostream& os, const vector<vector<T>>& V) {
  long long N = V.size();
  for (long long i = 0; i < N - 1; i++) cout << V[i] << "\n";
  cout << V[N - 1];
  return os;
}
template <typename T, typename S>
ostream& operator<<(ostream& os, pair<T, S> const& P) {
  os << P.first << ' ' << P.second;
  return os;
}
template <typename T>
ostream& operator<<(ostream& os, set<T>& S) {
  auto it = S.begin();
  while (it != S.end()) {
    os << *it;
    if (next(it, 1) != S.end()) os << ' ';
    it++;
  };
  return os;
}
template <typename T>
ostream& operator<<(ostream& os, deque<T>& q) {
  for (auto it = q.begin(); it < q.end(); it++) {
    os << *it;
    if (it + 1 != q.end()) os << " ";
  }
  return os;
}
long long gcd(long long a, long long b) { return b ? gcd(b, a % b) : a; }
long long lcm(long long a, long long b) { return a / gcd(a, b) * b; }
long long mypow(long long x, long long n, long long m) {
  if (n == 0) return 1;
  if (n % 2 == 0)
    return mypow(x * x % m, n / 2, m);
  else
    return x * mypow(x, n - 1, m) % m;
}
long long scomb(long long n, long long r) {
  if (r < 0 || r > n) return 0;
  if ((n - r) < r) r = n - r;
  long long a = 1;
  for (long long i = n; i > n - r; --i) {
    a = a * i;
  }
  for (long long i = 1; i < r + 1; ++i) {
    a = a / i;
  }
  return a;
}
vector<long long> vis(vector<long long>& v) {
  vector<long long> S(v.size() + 1);
  for (long long i = 1; i < S.size(); i++) S[i] += v[i - 1] + S[i - 1];
  return S;
}
long long digit(long long k, long long i) {
  string s = to_string(k);
  return s[s.size() - i] - '0';
}
void press(vector<long long>& v) {
  v.erase(unique((v).begin(), (v).end()), v.end());
}
vector<long long> zip(vector<long long> b) {
  long long Z = b.size();
  pair<long long, long long> p[Z + 10];
  long long a = b.size();
  vector<long long> l(a);
  for (long long i = 0; i < a; i++) p[i] = make_pair(b[i], i);
  sort(p, p + a);
  long long w = 0;
  for (long long i = 0; i < a; i++) {
    if (i && p[i].first != p[i - 1].first) w++;
    l[p[i].second] = w;
  }
  return l;
}
vector<long long> beki2V() {
  vector<long long> a(63);
  long long q = 1;
  for (long long i = 0; i < 63; i++) {
    a[i] = q;
    q *= 2;
  }
  return a;
}
vector<long long> beki2 = beki2V();
long long modiv(long long a, long long b) {
  return a * mypow(b, 1000000007 - 2, 1000000007) % 1000000007;
}
long long SMALLER(vector<long long>& a, long long x) {
  return lower_bound(a.begin(), a.end(), x) - a.begin();
}
long long orSMALLER(vector<long long>& a, long long x) {
  return upper_bound(a.begin(), a.end(), x) - a.begin();
}
long long BIGGER(vector<long long>& a, long long x) {
  return a.size() - orSMALLER(a, x);
}
long long orBIGGER(vector<long long>& a, long long x) {
  return a.size() - SMALLER(a, x);
}
long long COUNT(vector<long long>& a, long long x) {
  return upper_bound((a).begin(), (a).end(), x) -
         lower_bound((a).begin(), (a).end(), x);
}
long long maxind(vector<long long>& a) {
  return max_element((a).begin(), (a).end()) - a.begin();
}
long long minind(vector<long long>& a) {
  return min_element((a).begin(), (a).end()) - a.begin();
}
vector<long long> stpowV() {
  vector<long long> a(300005);
  a[0] = 1;
  for (long long i = 1; i <= 300004; i++) a[i] = a[i - 1] * i % 1000000007;
  return a;
}
signed main() {
  cin.tie(0);
  cout.tie(0);
  ios::sync_with_stdio(0);
  cout << fixed << setprecision(12);
  long long n;
  cin >> n;
  map<pair<long long, long long>, long long> ct;
  for (long long i = 0; i < n; i++) {
    long long qw, er;
    cin >> qw >> er;
    if (qw == 0 && er == 0)
      continue;
    else if (qw == 0) {
      ct[make_pair(0, 1)]++;
      if (ct[make_pair(1, 0)] == 0) ct[make_pair(1, 0)] = 0;
      continue;
    } else if (er == 0) {
      ct[make_pair(1, 0)]++;
      if (ct[make_pair(0, 1)] == 0) ct[make_pair(0, 1)] = 0;
      continue;
    }
    long long ty = gcd(abs(qw), abs(er));
    if (ty == 0) continue;
    qw /= ty;
    er /= ty;
    if (qw < 0) {
      qw *= -1;
      er *= -1;
    }
    pair<long long, long long> are = make_pair(qw, er);
    ct[are]++;
    are.second *= -1;
    swap(are.first, are.second);
    if (are.first < 0) {
      are.first *= -1;
      are.second *= -1;
    }
    if (ct[are] == 0) ct[are] = 0;
  }
  mint ans = 1;
  for (auto p : ct) {
    auto k = p.first;
    auto v = p.second;
    long long qw, er, pre;
    pair<long long, long long> ver = k;
    ver.second *= -1;
    swap(ver.first, ver.second);
    if (ver.first < 0) {
      ver.first *= -1;
      ver.second *= -1;
    }
    qw = ct[ver];
    if (qw == 0 && v == 0) continue;
    mint aa = mypow(2, qw, 1000000007);
    aa += mypow(2, v, 1000000007);
    aa -= 1;
    ans *= aa;
    ct[ver] = 0;
    ct[k] = 0;
  }
  ans -= 1;
  cout << ans << "\n";
  return 0;
}
