#include <bits/stdc++.h>
using namespace std;
namespace BinaryOperation {
template <typename T>
struct Sum {
  T operator()(T const& lhs, T const& rhs) { return lhs + rhs; }
};
template <typename T>
struct Min {
  T operator()(T const& lhs, T const& rhs) { return min(lhs, rhs); }
};
template <typename T>
struct Max {
  T operator()(T const& lhs, T const& rhs) { return max(lhs, rhs); }
};
}  // namespace BinaryOperation
template <typename T, template <typename> class Operation>
class IntervalTree {
 public:
  IntervalTree() : tree(size << 1) {}
  void init(vector<T> const& leaves) {
    copy(leaves.begin(), leaves.end(), tree.begin() + size);
    for (int i = size - 1; i > 0; --i) updateNode(i);
  }
  void update(int node, T const& newValue) {
    tree[node += size] = newValue;
    node >>= 1;
    while (node > 0) {
      updateNode(node);
      node >>= 1;
    }
  }
  T get(int l, int r, T def = T()) {
    T result = def;
    for (l += size, r += size; l <= r; l >>= 1, r >>= 1) {
      if (l & 1) result = operation(result, tree[l++]);
      if (~r & 1) result = operation(result, tree[r--]);
    }
    return result;
  }
  T get(int node) { return tree[size + node]; }

 private:
  void updateNode(int node) {
    tree[node] = operation(tree[node << 1], tree[node << 1 | 1]);
  }
  enum { size = 1 << 20 };
  Operation<T> operation;
  vector<T> tree;
};
IntervalTree<long long, BinaryOperation::Sum> sumHeightTree;
IntervalTree<long long, BinaryOperation::Sum> cntHeightTree;
void updateCnt(int index, int delta) {
  int const curValue = cntHeightTree.get(index);
  cntHeightTree.update(index, curValue + delta);
}
void updateSum(int index, long long delta) {
  long long const curValue = sumHeightTree.get(index);
  sumHeightTree.update(index, curValue + delta);
}
int main() {
  ios_base::sync_with_stdio(false);
  int n, q;
  cin >> n >> q;
  vector<int> h(n);
  for (int i = (0); i < ((n)); ++i) cin >> h[i];
  set<long long> allHeights(h.begin(), h.end());
  vector<pair<int, pair<long long, long long> > > queries(q);
  for (int i = (0); i < ((q)); ++i) {
    cin >> queries[i].first;
    if (queries[i].first == 1) {
      cin >> queries[i].second.first >> queries[i].second.second;
      allHeights.insert(queries[i].second.second);
    } else {
      cin >> queries[i].second.first;
      allHeights.insert(queries[i].second.first);
    }
  }
  allHeights.insert(0);
  allHeights.insert(1e18 + 1e9);
  map<long long, int> heightMap;
  {
    vector<long long> allHeightsOrder(allHeights.begin(), allHeights.end());
    for (int i = (0); i < (((int)allHeightsOrder.size())); ++i) {
      heightMap[allHeightsOrder[i]] = i;
    }
  }
  for (int i = (0); i < ((n)); ++i) {
    int const nodeIndex = heightMap[h[i]];
    updateCnt(nodeIndex, 1);
    updateSum(nodeIndex, h[i]);
  }
  for (int i = (0); i < ((q)); ++i) {
    if (queries[i].first == 1) {
      int const p = queries[i].second.first - 1;
      int const newValue = queries[i].second.second;
      int const oldValue = h[p];
      int const oldNodeIndex = heightMap[oldValue];
      int const newNodeIndex = heightMap[newValue];
      h[p] = newValue;
      updateCnt(oldNodeIndex, -1);
      updateCnt(newNodeIndex, 1);
      updateSum(oldNodeIndex, -oldValue);
      updateSum(newNodeIndex, newValue);
    } else {
      long long const v = queries[i].second.first;
      double l = 0, r = v + 2e9;
      for (int iters = (0); iters < ((300)); ++iters) {
        double const x = (l + r) / 2;
        auto it = heightMap.lower_bound(x);
        int const nodeIndex = it->second;
        int const cntLessX = cntHeightTree.get(0, nodeIndex);
        long long const sumLessX = sumHeightTree.get(0, nodeIndex);
        if (cntLessX * x - sumLessX + 1e-6 >= v)
          r = x;
        else
          l = x;
      }
      printf("%.5lf\n", l);
    }
  }
  return 0;
}
