#include<bits/stdc++.h>
#include <climits>
using namespace std;
const int maxn = 2e5+10;
int num[maxn][2];int maxbe = 0;int mined = INT_MAX;

int main()
{
    int n;cin >> n;int x;
    for(int i = 1;i<=2*n;i++) {
        cin >> x;
        if(!num[x][0]) {
            num[x][0] = i;
            if(i>maxbe) {
                maxbe = i;
            }
        }
        else { 
            num[x][1] = i;
            if(i<mined) {
                mined = i;
            }
        }
    }
    long long sum = 0;
    for(int i = 1;i<=n;i++) {
        sum+=num[i][1] - num[i][0] - 1;
    }

    if(mined < maxbe) sum+= (maxbe-mined)*2;

    cout << sum;
}

看没人写题解,所以来水一篇(,,・ω・,,),算是比较简单的思维题

首先,我们用一个二维数组存放任意一个数的两处位置,那么我们很容易发现,num[k][1] > num[k][0]恒成立

题目中,小红要交换一次达成最大权值,所以我们来思考什么方式可以达成最大权值

首先,我们考察三种可能,包裹,重叠以及相离,这些到底是什么意思,我下面会一一解释

包裹

小红只能交换一次,所以交换相同的数字没有意义,所以,交换的数字一定是不同的,而包裹则是其中的一种可能的数字排列方式,例如

1xxx2xxxx2xxx1

这时,如果我们尝试交换1和2,这就构成了包裹

这里,我们很容易发现,无论怎么交换,权值一定不变,所以当交换的两个数产生如此排列时,我们不应该交换

重叠

同理,重叠也是其中的一种方式,例如

1xxxx2xxx1xxx2

1和2之间有着部分重叠,同样,在这种情况下,交换要么不变,要么变小,所以没有意义,我们也不换

相离

同样,例如

1xxxx1xxx2xxxx2

1和2之间的空间毫无交集,在这种情况下,交换1的最后一位和2的第一位必定会增大

到这里,很明显,我们的任务变成了,寻找最大相离的情况,如果没有,不变,有,加上增长的,最后输出

代码实现

for(int i = 1;i<=2*n;i++) {
        cin >> x;
        if(!num[x][0]) {
            num[x][0] = i;
            if(i>maxbe) {
                maxbe = i;
            }
        }
        else { 
            num[x][1] = i;
            if(i<mined) {
                mined = i;
            }
        }
    }
num[k][0]代表一个数字的第一位,num[k][1]代表一个数字的第二位
long long sum = 0;
    for(int i = 1;i<=n;i++) {
        sum+=num[i][1] - num[i][0] - 1;
    }

    if(mined < maxbe) sum+= (maxbe-mined)*2;

    cout << sum;
maxbe 代表所有数字第一位的最大值,mined代表所有数字第二位的最小值,如果maxbe > mined 则其为最大相离,反之,则不存在相离,直接输出即可,这是这段代码的主逻辑

蒟蒻实力浅薄,各路大佬轻喷(≧∀≦)ゞ