1. 程式人生 > 其它 >b_mt_成為漂亮序列的操作次數(建圖+統計連通塊個數)

b_mt_成為漂亮序列的操作次數(建圖+統計連通塊個數)

有一個長度為n (n為偶數)的序列A,序列中的數都是介於[1,100000的整數。
我想把這個序列變得漂亮後再送回給你。
你覺得一個序列是漂亮的當且僅當這個序列的前一半和後 一半是一樣的,即對於1< =i< =n/2都滿足A[i1= A[i+n/2]。

我可以按進行以下操作任意次:選擇兩個介於[1,100000]之間的數x和y,然後將序列A中所有值為x的數替換為y。
我想知道他最少需要操作多少次可以把序列變成漂亮的。

輸入描述
第一行是一個整數n,表示序列的長度。資料保證n為偶數。
第二行有n個用空格隔開的整數,第i個數表示A[的值。資料保證1< =A[<=100000。
輸出描述
輸出我需要的最少操作次數。
輸入
10
4 2 1 5 2 10 2 1 5 8
輸出:2

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int N = 1e5 +5;
vector<int> g[N];
int vis[N];

void dfs(int u) {
    vis[u] = 1;
    for (int v : g[u]) {
        if (!vis[v]) {
            dfs(v);
        }
    }
}
void f3() {
    int n;
    cin >> n;
    vector<int> a(n);
    unordered_set<int> nums;
    for (int i = 0; i < n; i++)  {
        cin >> a[i];
    }

    for (int i = 0; i < n/2; i++) {
        if (a[i] != a[i + n / 2]) {
            g[a[i]].push_back(a[i + n / 2]);
            g[a[i + n / 2]].push_back(a[i]);
            nums.insert(a[i]);
            nums.insert(a[i + n / 2]);
        }
    }
    int ltk = 0;
    for (int t : nums) {
        if (!vis[t]) {
            dfs(t);
            ltk++;
        }
    }
    cout << nums.size() - ltk << '\n';
}
int main() {
    std::ios::sync_with_stdio(false); cin.tie(0); cout.tie(0);
    f3();
    return 0;
}