Link: C. Berry Jam

C. Berry Jam

Description:
Karlsson has recently discovered a huge stock of berry jam jars in the basement of the house. More specifically, there were 2n jars of strawberry and blueberry jam.

All the 2n jars are arranged in a row. The stairs to the basement are exactly in the middle of that row. So when Karlsson enters the basement, he sees exactly n jars to his left and n jars to his right.

For example, the basement might look like this:

Being the starightforward man he is, he immediately starts eating the jam. In one minute he chooses to empty either the first non-empty jar to his left or the first non-empty jar to his right.

Finally, Karlsson decided that at the end the amount of full strawberry and blueberry jam jars should become the same.

For example, this might be the result:

He has eaten 1 jar to his left and then 5 jars to his right. There remained exactly 3 full jars of both strawberry and blueberry jam.
Jars are numbered from 1 to 2n from left to right, so Karlsson initially stands between jars n and n+1.

What is the minimum number of jars Karlsson is required to empty so that an equal number of full strawberry and blueberry jam jars is left?

Your program should answer t independent test cases.

Input
The first line contains one integer t (1≤t≤1000) — the number of test cases.

The first line of each test case contains a single integer n (1≤n≤1e5).

The second line of each test case contains 2n integers a1,a2,…,a2n (1≤ai≤2) — ai=1 means that the i-th jar from the left is a strawberry jam jar and ai=2 means that it is a blueberry jam jar.

It is guaranteed that the sum of n over all test cases does not exceed 1e5.

Output
For each test case print the answer to it — the minimum number of jars Karlsson is required to empty so that an equal number of full strawberry and blueberry jam jars is left.

Example
input
4
6
1 1 1 2 2 1 2 1 2 1 1 2
2
1 2 1 2
3
1 1 1 1 1 1
2
2 1 1 1
output
6
0
6
2
Note
The picture from the statement describes the first test case.

In the second test case the number of strawberry and blueberry jam jars is already equal.

In the third test case Karlsson is required to eat all 6 jars so that there remain 0 jars of both jams.

In the fourth test case Karlsson can empty either the second and the third jars or the third and the fourth one. The both scenarios will leave 1 jar of both jams.

Problem solving:
这道题的意思就是你现在在中间,左边有n瓶果酱,右边有n瓶果酱。有两种不同的果酱,你可以从中间往两边选果酱吃,问你最少选几次可以让剩下的两种果酱的数量相等。
因为只有两种果酱,所以我们可以用1和-1表示。 然后维护一个前缀和数组,这个数组中的值就可以代表前i个果酱里面有几个是多余的(即大于另一个果酱的个数)因为是要从中间开始往两边吃。所以我们对n左右分别考虑。对左边存储每一个数出现的最后一个位置,用map存一下。然后再看n右边,用当前位置的前缀和数组的值减去最后一个位置的值(这个算出来的就是当前位置到最后距离两种果酱数量相等还差几个以及哪种果酱,1和-1表示)。如果这个值在前面出现过,说明有一种满足要求的情况出现。此时答案就是(i-map[a[i]]),因为这里还需要对0初始化为0,所以需要用到map中的find,然后每次更新答案最小值即可。

说不一定能说清,解释一下样例可能会清楚一点

2  1 | 1 1
-1 1 | 1 1
-1 0   1 2

mid=a[i]-a[2*n],ans=1e9
i=2 mid=-2 find=end
i=3 mid=-1 find!=end  ans=min(ans,i-map[a[i]])=2
i=4 mid=0  find!=end  ans=min(ans,i-map[a[i]])=2
ans=2

Code:

#include <bits/stdc++.h>
using namespace std;
const int maxn = 2e5 + 10;
int       a[maxn];
int main()
{
    int t, n;
    cin >> t;
    while (t--)
    {
        cin >> n;
        map<int, int> ma;
        ma[0] = 0;
        int           ans = 1e9;
        for (int i = 1, x; i <= 2 * n; i++)
        {
            cin >> x;
            a[i]  = (x == 1 ? 1 : -1);
            a[i] += a[i - 1];
            if (i <= n)
                ma[a[i]] = i;
        }
        for (int i = n; i <= 2 * n; i++)
        {
            int x = a[i] - a[2 * n];
            if (ma.find(x) != ma.end())
                ans = min(ans, i - ma[x]);
        }
        cout << ans << endl;
    }
}