Codeforces 1243B2 Character Swap (Hard Version)

思路:

1.统计所有字符出现次数,如果均为偶数,则必定可以移成一样的字符串;
2.从前往后同时遍历两个字符串,如果两个位置不一样,我们设法使第二个字符串的这个位置和第一个字符串的这个位置相等;设第一个字符串此位置为a,第二个字符串这里是b,那么我们就在第一个字符串后面找a,互换一次即可,找不到那第二个字符串后面必定有a,那就利用第一个字符串后面某位置,互换两次即可;

代码:

#include<bits/stdc++.h>
using namespace std;
typedef pair<int,int> P;
typedef long long LL;
#define fi first
#define sc second
#define pb(a) push_back(a)
#define mp(a,b) make_pair(a,b)
#define pt(a) cerr<<a<<"---
"
#define rp(i,n) for(int i=0;i<n;i++)
#define rpn(i,n) for(int i=1;i<=n;i++)
int main(){
	ios::sync_with_stdio(false);
	cin.tie(nullptr);
	int k; cin>>k;
	while(k--){
		int n; cin>>n;
		string a,b; cin>>a>>b;
		map<char,int> cnt;
		rp(i,n) cnt[a[i]]++,cnt[b[i]]++;
		vector<P> v;
		for(auto x:cnt){
			if(x.sc&1){
				cout<<"No
"; goto out;
			}
		}
		cout<<"Yes
";
		rp(i,n){
			if(a[i]!=b[i]){
				int pos=a.rfind(a[i]);
				if(pos!=i) v.pb(mp(pos,i)),swap(a[pos],b[i]);
				else{
					pos=b.rfind(a[i]);
					v.pb(mp(i+1,pos)); v.pb(mp(i+1,i));
					swap(a[i+1],b[pos]); swap(a[i+1],b[i]);
				}
			}
		}
		cout<<v.size()<<'
';
		for(auto x:v) cout<<x.fi+1<<' '<<x.sc+1<<'
';
		out:;
	}
	return 0;
}
原文地址:https://www.cnblogs.com/yuhan-blog/p/12308747.html