#include <iostream>
#include <vector>
#include <stack>
#include <algorithm>
#include <functional>
#include <map>
#include <stack>
#include <set>
#include <sstream>
#include <iomanip>
#include <memory>
#include <stdexcept>
#include <random>
#include <bitset>
#include <queue>

using int8 = int_fast8_t;
using uint8 = uint_fast8_t;
using int16 = int_fast16_t;
using uint16 = uint_fast16_t;
using int32 = int_fast32_t;
using uint32 = uint_fast32_t;
using int64 = int_fast64_t;
using uint64 = uint_fast64_t;
using f32 = float;
using f64 = double;

using namespace std;

template <typename _ty>
uint64 argmax(const vector<_ty> & v)
{
    uint64 amax = 0;
    for (uint64 i = 1; i < v.size(); ++i)
    {
        if (v[amax] < v[i])
        {
            amax = i;
        }
    }

    return amax;
}

template <typename _ty>
uint64 argmin(const vector<_ty> & v)
{
    uint64 amin = 0;
    for (uint64 i = 1; i < v.size(); ++i)
    {
        if (v[i] < v[amin])
        {
            amin = i;
        }
    }

    return amin;
}

template <typename _ty>
_ty max(const vector<_ty> & v)
{
    return v[argmax(v)];
}

template <typename _ty>
_ty min(const vector<_ty> & v)
{
    return v[argmin(v)];
}

const double eps = 1e-5;

uint64 gcd(uint64 a, uint64 b)
{
    if (b == 0)
    {
        return a;
    }
    return gcd(b, a % b);
}

struct point
{
    int64 x;
    int64 y;

    point() : x(0), y(0)
    {
    }

    point(int64 x, int64 y) : x(x), y(y)
    {
    }

    int64 operator ()(const point & p) const
    {
        return x * p.x + y * p.y;
    }

    int64 operator [](const point & p) const
    {
        return x * p.y - p.x * y;
    }

    bool operator ==(const point & p) const
    {
        return x == p.x && y == p.y;
    }

    friend istream & operator >> (istream & in, point & p);
};

istream & operator >> (istream & in, point & p)
{
    return in >> p.x >> p.y;
}

struct line
{
    point from;
    point to;

    line()
    {
    }

    line(const point & from, const point & to) : from(from), to(to)
    {
    }

    friend istream & operator >> (istream & in, line & l);
};

istream & operator >> (istream & in, line & l)
{
    return in >> l.from >> l.to;
}

f64 area(const vector<point> & p)
{
    int64 a = p.back()[p[0]];
    for (uint64 i = 1; i < p.size(); ++i)
    {
        a += p[i - 1][p[i]];
    }

    return a / 2.0;
}


template <typename _ty, typename _function_type>
class Segment_Tree
{
    vector<_ty> m_tree;

    _function_type m_function;


    uint64 next_power(uint64 x)
    {
        uint64 n = 1;
        while (n < x)
        {
            n <<= 1;
        }

        return n;
    }

    _ty get(uint64 v, uint64 l, uint64 r, uint64 tl, uint64 tr)
    {
        if (r <= tl || tr <= l)
        {
            return _ty{};
        }
        if (tl <= l && r <= tr)
        {
            return m_tree[v];
        }

        uint64 m = l + (r - l) / 2;
        return m_function(
                get(2 * v, l, m, tl, tr),
                get(2 * v + 1, m, r, tl, tr)
        );
    }

public:
    Segment_Tree() : m_tree(), m_function() {}
    explicit Segment_Tree(const vector<_ty> & p) : m_tree(), m_function()
    {
        rebuild(p);
    }

    void rebuild(const vector<_ty> & p)
    {
        uint64 size = next_power(p.size());
        m_tree.resize(2 * size);

        for (uint64 i = 0; i < p.size(); ++i)
        {
            m_tree[i + size] = p[i];
        }

        for (uint64 i = size; i-- > 1;)
        {
            m_tree[i] = m_function(m_tree[2 * i], m_tree[2 * i + 1]);
        }
    }

    void update(uint64 index, const _ty & value)
    {
        m_tree[index += m_tree.size() / 2] = value;
        while (index /= 2)
        {
            m_tree[index] = m_function(m_tree[2 * index], m_tree[2 * index + 1]);
        }
    }

    _ty get(uint64 l, uint64 r)
    {
        return get(1, 0, m_tree.size() / 2, l, r);
    }
};

struct node
{
    uint64 value;
    uint64 index;
    uint64 sum;

    node() : value(0), index(0), sum(0) {}
    node(uint64 value, uint64 index) : value(value), index(index), sum(value) {}
};

struct cmp
{
    node operator ()(const node & a, const node & b) const
    {
        node res;
        res.sum = a.sum + b.sum;
        if (a.value > b.value)
        {
            res.value = a.value;
            res.index = a.index;
        }
        else
        {
            res.value = b.value;
            res.index = b.index;
        }
        return res;
    }
};

int main()
{
    ios::sync_with_stdio(false);
    cin.tie(nullptr);
    cout.tie(nullptr);

    uint64 n = 0;
    cin >> n;

    vector<int64> a(n);
    for (uint64 i = 0; i < n; ++i)
    {
        cin >> a[i];
    }

    int64 amx = argmax(a);
    int64 amn = argmin(a);

    vector<pair<uint64, uint64>> ananas;
    if (abs(a[amx]) < abs(a[amn]))
    {
        for (uint64 i = 0; i < n; ++i)
        {
            ananas.emplace_back(amn + 1, i + 1);
        }

        for (uint64 i = n; i-- > 1;)
        {
            ananas.emplace_back(i + 1, i);
        }
    }
    else
    {
        for (uint64 i = 0; i < n; ++i)
        {
            ananas.emplace_back(amx + 1, i + 1);
        }

        for (uint64 i = 1; i < n; ++i)
        {
            ananas.emplace_back(i, i + 1);
        }
    }

    cout << ananas.size() << '\n';
    for (const auto & p : ananas)
    {
        cout << p.first << ' ' << p.second << '\n';
    }

    return 0;
}

Measured memory_bytes: 256