Title address: https://codeforces.com/gym/101606
This question can be regarded as The magic of CSL The advanced level of this problem
meaning of the title
Give the initial sequence. Ask how to restore the initial sequence to the original sequence after ascending.
Output the position of each switch, (A,B) and meet the requirements of s[A-1] ≥ s[B-1], i.e. the A and B switches
Solving problems
First, these characters are discretized, s[i].id records the input order of each letter, and sort s the input strings in ascending order
Traverse the ascending sequence in turn. When s[i].id!=i, it means that the position of the letter changes when the initial string is sort
Method 1:
Only two letters are exchanged at a time, and the id corresponding to the letter is not exchanged, according to the The magic of CSL The circle in this question looks down for the subscript and exchanges with the letter at the beginning every time
Method 2:
The id corresponding to two letters and two letters are exchanged each time, and the location of the next exchange: the id corresponding to the starting position (new id value) and the starting position
Let's do an example by hand: abdac
The output of these two methods should be
4 2
5 2
2 3
The output result can not be the same as the sample, after all, there are many methods!
Be sure to meet the output conditions!! s[A-1]≥s[B-1]
ac code
Method 1: exchange only letters, not id
#include <iostream> #include <algorithm> #include <string.h> #include <ctype.h> #include <set> #include <cmath> #include <queue> #include <stack> #include <map> #include <sstream> #define maxn 1005 typedef long long ll; using namespace std; int vis[maxn]={0}; struct node{ char ch; int id; friend bool operator <(node a,node b) { return a.ch<b.ch; } }s[maxn]; int main() { //freopen("/Users/zhangkanqi/Desktop/11.txt","r",stdin); char s1[maxn]; cin>>s1; int len=strlen(s1); for(int i=0;i<len;i++) { s[i].ch=s1[i]; s[i].id=i; } sort(s,s+len); for(int i=0;i<len;i++) { if(s[i].id==i||vis[i]) continue; int start=i,next=s[start].id; while(next!=start) { vis[next]=1; if(s[start].ch>=s[next].ch) printf("%d %d\n",start+1,next+1); else printf("%d %d\n",next+1,start+1); swap(s[start].ch,s[next].ch); next=s[next].id; } } return 0; }
Method 2: exchange letters and IDS
#include <iostream> #include <algorithm> #include <string.h> #include <ctype.h> #include <set> #include <cmath> #include <queue> #include <stack> #include <map> #include <sstream> #define maxn 1005 typedef long long ll; using namespace std; int vis[maxn]={0}; struct node{ char ch; int id; friend bool operator <(node a,node b) { return a.ch<b.ch; } }s[maxn]; int main() { //freopen("/Users/zhangkanqi/Desktop/11.txt","r",stdin); char s1[maxn]; cin>>s1; int len=strlen(s1); for(int i=0;i<len;i++) { s[i].ch=s1[i]; s[i].id=i; } sort(s,s+len); for(int i=0;i<len;i++) { if(s[i].id==i||vis[i]) continue; while(s[i].id!=i) { int now=i,next=s[now].id; vis[now]=1;vis[next]=1; if(s[now].ch>=s[next].ch) printf("%d %d\n",now+1,next+1); else if(s[next].ch>=s[now].ch) printf("%d %d\n",next+1,now+1); swap(s[now],s[next]); } } return 0; }