/* *为了用set写被折磨了好久,其实没多大事,不了解set建议百度一下 要解决本题要两步: 第一步: 计算两数组自身去重分别需要操作多少次 第二步: 计算自身去重后,消除两数组的重合部分需要操作多少次 对于第二步,若自身去重后,两数组无重合,直接取两数组操作次数中的大的那一个。 否则,需要根据第一步两个数组操作次数大小进行讨论, */ #include<bits/stdc++.h> #define int long long using namespace std; signed main() { int n; cin>>n; vector <int> a(n+1,0),b(n+1,0); set <int> p1,p2,p;//用set自带的去重功能,方便求重复的数字个数 for(int i=1;i<=n;i++) { cin>>a[i]; p1.insert(a[i]);//p1表示第一组去重后的集合 } for(int i=1;i<=n;i++) { cin>>b[i]; p2.insert(b[i]);//p2表示第二组去重后的集合 } int ans1 = n-p1.size();//ans1记录第一组中重复的数的总数 int ans2 = n-p2.size();//ans2记录第二组中重复的数的总数 for(auto i:p1) { p.insert(i);//p表示(p1 U p2)的集合 } for(auto j:p2) { p.insert(j); } if(p1.size()+p2.size()==p.size())// p1 + p2 = p1 U p2说明集合无交集,不用后进行下一步, { cout<<max(ans1,ans2); return 0; } int num=p1.size()+p2.size()-p.size();//p1 ∩ p2 = p1 + p2 - (p1 U p2) 重合个数(单求自身去重两数组最小操作次数=(重合个数+1)/2) if(ans1==ans2)//第一步操作次数相同 cout<<ans1+(num+1)/2; //(num+1)是因为重合个数有奇数 else if(ans1>ans2) { if(num+ans2<=ans1)//若重合个数(大于最小操作次数)加上ans2还是小于等于ans1,就取ans1 cout<<ans1; else{//若有多余,还需要的最小操作次数=(多的个数+1)/2 num=num+ans2-ans1; cout<<ans1+(num+1)/2; } } else{ if(num+ans1<=ans2) cout<<ans2; else{ num=num+ans1-ans2; cout<<ans2+(num+1)/2; } } }