版权声明:_ https://blog.csdn.net/lunch__/article/details/82655579
这个题做法好神奇啊… 数据完全没有开满
我们把所输入的矩阵二的最后一列排序 那么就得到了矩阵的第一列
我们考虑从矩阵的第一列推出第 行
我们已经知道了第 行的第一位数是什么
然后根据它的矩阵变换规则 把第一个数移到最后一位
我们输入的序列可以知道这个数在这一行对应的第一位是什么
这样一直推下去就得出答案了 推的过程中如果出现了环那就是无解的
举个栗子来理解一下下 11100 每一个数记录下它属于哪一行
排序后得到 00111 它隶属的行随着一起排序
我们就知道了矩阵2的一部分是这样的
0 x x x 1
0 x x x 1
1 x x x 1
1 x x x 0
1 x x x 0
假设求第 行 我们知道了第一位是什么
把第一位的 移到最后一行
变成了x x x 1 0
我们再找到第二行的第一位做最后一位的时候是在哪一行
在排序的时候我们记录下了这个状态
那么那一行的开头就是接下来的一位数
自己模拟一下理解起来不是很难 然后就做完了
不知道为什么用char比int快好几倍,用int就需要基数排序了
Codes
#include<bits/stdc++.h>
using namespace std;
const int N = 500000 + 10;
pair<char, int> a[N];
int vis[N]; char ans[N];
int main() {
#ifndef ONLINE_JUDGE
freopen("test.in", "r", stdin);
freopen("test.out", "w", stdout);
#endif
int n, k; int cnt = 0;
scanf("%d", &n), k = 1;
for(int i = 1; i <= n; ++ i)
cin >> a[i].first, a[i].second = i;
sort(a + 1, a + n + 1);
for(int i = 1; i <= n; ++ i) {
if(vis[k]) return puts("No Solution"), 0;
ans[++ cnt] = a[k].first;
k = a[vis[k] = k].second;
}
for(int i = 1; i <= cnt; ++ i) putchar(ans[i]);
return 0;
}