× HomeMath BoardArchiveType

You are given an array of integers, denoted as a1,a2,,ana_1, a_2, \ldots, a_n, where the integers can be positive, negative, or zero. You have the option to perform multiple operations on this array, with the possibility of not performing any operation at all.

Each operation allows you to select two indices, denoted as ii and jj, where 1i,jn1 \leq i, j \leq n, and they can be equal. After selecting ii and jj, you can update the array by setting aia_i to be equal to ai+aja_i + a_j, effectively adding the value of aja_j to aia_i.

The objective is to modify the array in such a way that it becomes non-decreasing, meaning that for all 1in11 \leq i \leq n-1, the value of aia_i should be less than or equal to the value of ai+1a_{i+1}. You are allowed to use a maximum of 50 operations to achieve this goal. It is not necessary to find the minimum number of operations; you only need to ensure that the array becomes non-decreasing within the limit of 50 operations and ai20|a_i|\le 20 for any ii and n20.n \le 20.

Solution:

Suppose we have an array that consists entirely of non-positive numbers. We can perform the following steps:

1. Select the elements at indices n1n-1 and nn, resulting in an1=an1+ana'_{n-1} = a_{n-1}+a_n.

2. Next, select the elements at indices n2n-2 and n1n-1. This yields an2=an2+an1a'_{n-2} = a_{n-2}+a'_{n-1}, which simplifies to an2=an2+an1+anan1+an=an2a'_{n-2} = a_{n-2}+a_{n-1}+a_n \le a_{n-1}+a_n = a'_{n-2}.

3. Continue this pattern until you reach the first two elements of the array. At this point, we have a1=a1+a2=a1+i=2naii=2nai=a2a_1' = a_1 +a_2' = a_1 + \sum_{i=2}^n a_i \le \sum_{i=2}^n a_i = a_2'.

Now, let's consider an array that contains at least one positive number. We can multiply the maximum positive number, awa_w, by 2 kk times until it exceeds 20. From this, we can infer that 2k202^k \ge 20, which implies k5k \ge 5.

Assuming aw50a_w \ge 50, we proceed as follows:

1. For a1a_1, we perform operations on the indices 11 and ww, resulting in a1=aw+a10a_1' = a_w +a_1 \ge 0.

2. For a2a_2, we perform operations on the pairs of indices (2,1)(2,1) and (2,w)(2,w). Thus, we have a2=2aw+a1+a2=aw+a1+aw+a2aw+a1=a1a_2' =2a_w +a_1+a_2=a_w +a_1 +a_w +a_2 \ge a_w +a_1 = a'_1.

3. For a3a_3, we perform operations on the pairs of indices (3,w)(3,w) and (3,2)(3,2), which yields a3=aw+a3+a2a2a_3' = a_w +a_3 +a_2' \ge a_2'.

We can continue this process. When we encounter awa_w, we perform operations on the pairs of indices (w,w)(w,w) and (w,w1)(w,w-1), resulting in aw=2aw+aw1aw1a'_w = 2a_w+a'_{w-1} \ge a_{w-1}'.

In summary, we have either taken at most n20n \le 20 steps (for the non-positive case) or no more than 2×(n1)+1+log2(40)log2(max(ai))2×19+1+5=44502\times(n-1)+1+\log_{2}(40)-\log_2(\max(a_i))\le 2 \times 19 +1 + 5 = 44 \le 50 steps (for the case with at least one positive number)

Sample Code (in C++):

 

#include <iostream>

#include <vector>

 

using namespace std;

 

int main() {

 

    // fast io

 

    ios_base::sync_with_stdio(false);

    cin.tie(NULL);

    cout.tie(NULL);

 

    int t;

    cin >> t;

    while (t--) {

        int n;

        cin >> n;

        vector<int> a(n);

        // Read the array.

        for (int i = 0; i < n; ++i) {

            cin >> a[i];

        }

        int maxid = 0;

        // Find the index of the maximum element.

        for (int i = 1; i < n; ++i) {

            if (a[i] > a[maxid]) {

                maxid = i;

            }

        }

        // If the maximum element is non-positive, we can perform at most n -1 steps.

        if (a[maxid] <= 0) {

            cout << n - 1 << endl;

            for(int i = n-2; i>= 0; --i) {

                cout << i + 1 << " " << i + 2 << endl;

            }

            continue;

        }

        // Otherwise, we can perform at most 2 * (n - 1) + 1 + log2(40) - log2(max(a[i])) steps.

        vector<pair<int, int>> ans;

        // first we perform operations so that a[maxid] is greater than 20.

 

        while (a[maxid] <= 20)

        {

            ans.push_back({maxid + 1, maxid + 1});

            a[maxid] *= 2;

        }

 

        // Then we perform operations (1, maxid +1), (2, maxid + 1), (2, 1), ... (maxid, maxid + 1), (maxid, maxid - 1), ... (maxid, 1).

       

        for (int i = 0; i < n; i++)

        {

            ans.push_back({i + 1, maxid + 1});

            if(i > 0) ans.push_back({i + 1, i });

        }

        cout << ans.size() << endl;

        for (auto p : ans)

        {

            cout << p.first << " " << p.second << endl;

        }

    }

    return 0;

}