#include <bits/stdc++.h>   using namespace std;   int arr[100005], lazy[4 * 100005], num, value;   bool flag;   struct Node {     int maxi, mini, one, two;   } tree[4 * 100005];   Node merge(Node a, Node b) {     Node temp;     int num = max(a.maxi, b.maxi);     temp.maxi = num, temp.one = num == a.maxi ? a.one : b.one;     num = min(a.mini, b.mini);     temp.mini = num, temp.two = num == a.mini ? a.two : b.two;     return temp;   }   void build(int node, int a, int b) {     if (a > b) return;     if (a == b) {       tree[node] = (Node){arr[a], arr[a], a, a};       return;     }     int left, right;     left = 2 * node + 1, right = 2 * node + 2;     build(left, a, (a + b) / 2);     build(right, (a + b) / 2 + 1, b);     tree[node] = merge(tree[left], tree[right]);   }   void lazy_update(int node, int a, int b) {     int left, right;     left = 2 * node + 1, right = 2 * node + 2;     tree[node].maxi -= lazy[node];     tree[node].mini -= lazy[node];     if (a != b) {       lazy[left] += lazy[node];       lazy[right] += lazy[node];     }     lazy[node] = 0;   }   void update(int node, int a, int b, int i, int j, int val) {     if (lazy[node]) lazy_update(node, a, b);     if (a > b || a > j || b < i) return;     if (a >= i && b <= j) {       lazy[node] = val;       lazy_update(node, a, b);       return;     }     int left, right;     left = 2 * node + 1, right = 2 * node + 2;     update(left, a, (a + b) / 2, i, j, val);     update(right, (a + b) / 2 + 1, b, i, j, val);     tree[node] = merge(tree[left], tree[right]);   }   void query(int node, int a, int b, int i, int j, int val) {     if (lazy[node]) lazy_update(node, a, b);     if (flag) return;     if (a > b || a > j || b < i) return;     if (val > tree[node].mini) {       if (a == b) {         flag = true;         num = a;         return;       }       int left, right;       left = 2 * node + 1, right = 2 * node + 2;       query(left, a, (a + b) / 2, i, j, val);       query(right, (a + b) / 2 + 1, b, i, j, val);     }   }   void find(int node, int a, int b, int i, int j) {     if (lazy[node]) lazy_update(node, a, b);     if (a > b || a > j || b < i) return;     if (a == b) {       value = tree[node].mini;       return;     }     int left, right;     left = 2 * node + 1, right = 2 * node + 2;     find(left, a, (a + b) / 2, i, j);     find(right, (a + b) / 2 + 1, b, i, j);   }   int main() {     int n, a, b, one, two, k = 0, diff;     scanf( %d , &n);     set<int> zero;     for (int i = 0; i < n; i++) {       scanf( %d , &arr[i]);       if (!arr[i]) zero.insert(i);     }     build(0, 0, n - 1);     zero.insert(n);     vector<pair<int, int> > vec;     while (true) {       if (lazy[0]) lazy_update(0, 0, n - 1);       if (tree[0].maxi == 0) break;       int index = tree[0].one, x, y;       y = *zero.upper_bound(index);       flag = false;       query(0, 0, n - 1, index + 1, y - 1, tree[0].maxi);       if (flag)         a = index, b = num - 1;       else         a = index, b = min(n - 1, y - 1);       update(0, 0, n - 1, a, b, 1);       vec.push_back(make_pair(a + 1, b + 1));     }     printf( %d n , vec.size());     for (int i = 0; i < vec.size(); i++)       printf( %d %d n , vec[i].first, vec[i].second);     return 0;   }