#include <bits/stdc++.h>
using namespace std;
using ll = long long;

template<typename T> constexpr function<T(T, T)> ex_assign(T initE) {
  return [&initE](const T& x, const T& y) -> const T { return (y == initE) ? x : y; };
}
template<typename T> constexpr function<T(T, int)> ex_multiplies(T initE) {
  return [&initE](const T& x, size_t y) -> const T { return (x == initE) ? x : x * y; };
}
template<typename T, typename E> struct LazySegmentTree {
  using F = function<T(T, T)>;
  using G = function<T(T, E)>;
  using H = function<E(E, E)>;
  using P = function<E(E, int)>;

  int n;
  T initT;
  E initE;
  F f;
  G g;
  H h;
  P p;
  vector<T> data;
  vector<E> lazy;

  LazySegmentTree() {}
  LazySegmentTree(int n_, F f, G g, H h, T initT = INT_MAX, E initE = INT_MAX,
      vector<T> v = vector<T>(), P p = [](E a, size_t b) { ++b; return a; })
      : f(f), g(g), h(h), initT(initT), initE(initE), p(p) {
    n = 1;
    while (n < n_) n *= 2;
    data.assign(n * 2 - 1, initT);
    lazy.assign(n * 2 - 1, initE);
    if (n_ == v.size()) build(v);
  }
  void build(vector<T> v) {
    for (int i = 0; i < v.size(); ++i) data[i + n - 1] = v[i];
    for (int i = n - 2; i >= 0; --i) {
      data[i] = f(data[i * 2 + 1], data[i * 2 + 2]);
    }
  }
  inline void eval(int len, int k) {
    if (lazy[k] == initE) return;
    if (k * 2 + 1 < n * 2 - 1) {
      lazy[k * 2 + 1] = h(lazy[k * 2 + 1], lazy[k]);
      lazy[k * 2 + 2] = h(lazy[k * 2 + 2], lazy[k]);
    }
    data[k] = g(data[k], p(lazy[k], len));
    lazy[k] = initE;
  }
  T update(int a, int b, E x, int k = 0, int l = 0, int r = -1) {
    if (r < 0) r = n;
    eval(r - l, k);
    if (b <= l || r <= a) return data[k];
    if (a <= l && r <= b) {
      lazy[k] = h(lazy[k], x);
      return g(data[k], p(lazy[k], r - l));
    }
    T vl = update(a, b, x, k * 2 + 1, l, (l + r) / 2);
    T vr = update(a, b, x, k * 2 + 2, (l + r) / 2, r);
    return data[k] = f(vl, vr);
  }
  T query(int a, int b, int k = 0, int l = 0, int r = -1) {
    if (r < 0) r = n;
    eval(r - l, k);
    if (b <= l || r <= a) return initT;
    if (a <= l && r <= b) return data[k];
    T vl = query(a, b, k * 2 + 1, l, (l + r) / 2);
    T vr = query(a, b, k * 2 + 2, (l + r) / 2, r);
    return f(vl, vr);
  }
};
//
// e.g.
//      |     f     |   g   |   h   |   initT   | initE |   p
// -----+-----------+-------+-------+-----------+-------+--------
//  RMQ | min / max |       |       | INF / 0   |       | (mult)
//  RSQ | plus      |       |       | 0         |       | (mult)
//  RUQ |           | (ass) | (ass) |           | INF   | (mult)
//  RAQ |           | plus  | plus  |           | 0     | (mult)
//
//  (ass)  := ex_assign;
//  (mult) := ex_multiplies;
//

const ll initT = 0;
const ll initE = 0;
const LazySegmentTree<ll, ll>::F f = plus<ll>();
const LazySegmentTree<ll, ll>::G g = plus<ll>();
const LazySegmentTree<ll, ll>::H h = plus<ll>();
const LazySegmentTree<ll, ll>::P p = ex_multiplies<ll>(initE);

map<ll, int> compress(vector<ll> v) {
  map<ll, int> zip;
  for (int i = 0; i < v.size(); i++) zip[v[i]] = -1;
  int idx = 1;
  for (auto& p : zip) p.second = idx++;
  return zip;
}

int main() {
  int q;
  cin >> q;
  vector<int> query(q);
  vector<ll> x(q, 0);
  vector<ll> y(q, 0);
  for (int i = 0; i < q; i++) {
    cin >> query[i];
    if (i > 0) {
      x[i] = x[i - 1];
      y[i] += y[i - 1];
    }
    if (query[i] == 1) {
      ll a, b;
      cin >> a >> b;
      x[i] = a;
      y[i] += b;
    }
  }
  auto zip = compress(x);
  int n = zip.size() + 2;
  vector<ll> unzip(n);
  unzip[0] = -1e15;
  unzip[n - 1] = 1e15;
  for (auto&& p : zip) unzip[p.second] = p.first;
  LazySegmentTree<ll, ll> seg(n, f, g, h, initT, initE);
  LazySegmentTree<ll, ll> cnt(n, f, g, h, initT, initE);
  LazySegmentTree<ll, ll> sum(n, f, g, h, initT, initE);
  for (int i = 0; i < q; i++) {
    if (query[i] == 1) {
      ll a = zip[x[i]];
      seg.update(0, a, -1);
      seg.update(a, n, 1);
      cnt.update(a, a + 1, 1);
      sum.update(a, a + 1, x[i]);
    } else {
      int ng = -1, ok = n - 1;
      while (ok - ng > 1) {
        int m = (ok + ng) / 2;
        ((seg.query(m, m + 1) >= 0) ? ok : ng) = m;
      }
      ll med = unzip[ok];
      ll ans = y[i];
      ans += (cnt.query(0, ok) - cnt.query(ok + 1, n)) * med;
      ans += (sum.query(0, ok) - sum.query(ok + 1, n)) * -1;
      cout << med << ' ' << ans << endl;
    }
  }
}


Measured memory_bytes: 25828