【ZR #540. 【19普轉提4】串串】題解
阿新 • • 發佈:2022-01-08
題目連結
題目
給定兩個長度為 \(n\) 的只包含'a','b','c'的字串\(s,t\)。
請打亂串 \(s\),使得 \(\forall i,s_i \not= t_i\),且 \(s\) 字典序最小。
思路
對於 \(t\) 串中從前往後每一個字母,在 \(s\) 的剩餘可選字母中選字典序最小的。
如果 \(s\) 的剩餘字母中沒了,就往前找第一個可以替換的替換。
最後再對每種 \(t\) 中的字母按 \(s'\) 中的字典序排序。
總結
這道題當時在模擬賽時亂搞的做法,竟然A了。
這道題由於 \(n \leqslant 5000\), 我就直接按照後悔貪心的思想打了個 \(O(n^2)\)
\(O(n)\) 做法就不管了。
Code
// Problem: B. 【19普轉提4】串串 // Contest: UOJ - 麗澤普及2022交流賽day8 // URL: http://zhengruioi.com/contest/1074/problem/540 // Memory Limit: 512 MB // Time Limit: 1000 ms // // Powered by CP Editor (https://cpeditor.org) #include<bits/stdc++.h> using namespace std; //#define int long long inline int read(){int x=0,f=1;char ch=getchar(); while(ch<'0'||ch>'9'){if(ch=='-')f=-1; ch=getchar();}while(ch>='0'&&ch<='9'){x=(x<<1)+ (x<<3)+(ch^48);ch=getchar();}return x*f;} #define N 5010 //#define M //#define mo int n, m, i, j, k; int a[N], mp[5]; char s[N], t[N]; signed main() { // freopen("tiaoshi.in","r",stdin); // freopen("tiaoshi.out","w",stdout); n=read(); scanf("%s%s", t+1, s+1); for(i=1; i<=n; ++i) mp[t[i]-'a'+1]++; for(i=1; i<=n; ++i) { for(j=1; j<=3; ++j) if(mp[j]&&s[i]-'a'+1!=j) { a[i]=j; --mp[j]; break; } if(j>3) { for(j=i; j>=1; --j) if(s[i]-'a'+1!=a[j]&&s[i]!=s[j]) { a[i]=a[j]; a[j]=s[i]-'a'+1; --mp[s[i]-'a'+1]; break; } } } for(i=n; i>=1; --i) for(j=1; j<i; ++j) if(s[i]==s[j]&&a[i]<a[j]) swap(a[i], a[j]); for(i=1; i<=n; ++i) printf("%c", (char)a[i]+'a'-1); return 0; }