题目大意
题目总结:秘密信息 (Secret message)
给定 k 条长度均为 n 的字符串(纸条)。你需要构造一个长度为 n 的目标字符串 S,满足以下要求:
样例解释
样例 1
输入:n=3,k=2,纸条为 abc 和 baa
样例 2
输入:n=9,k=2,纸条为 iiinnnfff 和 nnfiffinn
-
尝试 d=1:无法找到一个字符在所有 9 个位置都出现。
-
尝试 d=3:寻找长度为 3 的字符串 t,使得 S=t+t+t 满足条件。
-
检查:若 t="inf",则 S="infinfinf"。
- 第 0, 3, 6 位:‘i’ 分别在纸条 1, 2, 2 中出现。
- 第 1, 4, 7 位:‘n’ 分别在纸条 1, 1, 1 中出现。
- 第 2, 5, 8 位:‘f’ 分别在纸条 2, 1, 2 中出现。
-
输出:infinfinf
样例 3
输入:n=4,k=2,纸条为 acbd 和 bdac
思路讲解
其实说白了这道题目就是想让你找一个字符串,一个字符串集的这个最小循环子串。啊,也就是找其最小循环节,但是其最小循环节呢是严格的这个最小循环节长度(即题目中的信息度),就是它不能够呃就是它不能够比如说呃roate,不能够呃循环移动的那种循环节,它是比较严格的那种循环节。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30
| auto check=[&](ll len,bool gen_ans=false) -> bool { vector<vector<int>> bi=gen_bi(0,len); for (ll i=len;i<N;i+=len) { bi=fac_and(bi,gen_bi(i,len)); } for (int i=0;i<len;++i) { bool ok=false; for (int j=0;j<26;++j) { if (bi[i][j]) { if (gen_ans) { ans.push_back('a'+j); } ok=true; break; } } if (!ok) { return false; } } if (gen_ans) { string back_up=ans; for (int i=2;i<=N/len;++i) { ans+=back_up; } } return true; };
|
AC代码
https://codeforces.com/contest/2194/submission/361977470
源代码
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132
|
#include <bits/stdc++.h> #define all(vec) vec.begin(),vec.end() #define lson(o) (o<<1) #define rson(o) (o<<1|1) #define SZ(a) ((long long) a.size()) #define debug(var) cerr << #var <<":"<<var<<"\n"; #define cend cerr<<"\n-----------\n" #define fsp(x) fixed<<setprecision(x)
using namespace std;
using ll = long long; using ull = unsigned long long; using DB = double;
using CD = complex<double>;
static constexpr ll MAXN = (ll)1e6+10, INF = (1ll<<61)-1; static constexpr ll mod = 998244353; static constexpr double eps = 1e-8; const double pi = acos(-1.0);
ll lT,testcase;
void Solve() { ll N,K; cin >> N >> K; vector<string> A(K); vector<vector<int>> i_ch_has(N,vector<int>(26)); for (int i=0;i<K;++i) { cin>>A[i]; for (int j=0;j<N;++j) { i_ch_has[j][A[i][j]-'a']=1; } } vector<ll> factor_n; for (int i=1;i<=N;++i) { if (N%i==0) { factor_n.push_back(i); } } string ans; auto gen_bi=[&](ll idx,ll len) -> vector<vector<int>> { vector<vector<int>> res(len,vector<int>(26)); for (ll i=idx;i<idx+len;++i) { for (int j=0;j<26;++j) { res[i-idx][j]|=i_ch_has[i][j]; } } return res; }; auto fac_and=[](vector<vector<int>> a, const vector<vector<int>> &b)->vector<vector<int>> { for (int i=0;i<a.size();++i) { for (int j=0;j<a[i].size();++j) { a[i][j]&=b[i][j]; } } return a; }; auto check=[&](ll len,bool gen_ans=false) -> bool { vector<vector<int>> bi=gen_bi(0,len); for (ll i=len;i<N;i+=len) { bi=fac_and(bi,gen_bi(i,len)); } for (int i=0;i<len;++i) { bool ok=false; for (int j=0;j<26;++j) { if (bi[i][j]) { if (gen_ans) { ans.push_back('a'+j); } ok=true; break; } } if (!ok) { return false; } } if (gen_ans) { string back_up=ans; for (int i=2;i<=N/len;++i) { ans+=back_up; } } return true; }; for (auto fac:factor_n) { if (check(fac)) { check(fac,true); break; } } cout<<ans<<"\n"; }
signed main() { ios::sync_with_stdio(false); cin.tie(nullptr); cout.tie(nullptr); #ifdef LOCAL cout.setf(ios::unitbuf); #endif
cin >> lT; for (testcase=1;testcase<=lT;++testcase) Solve(); return 0; }
|
心路历程(WA,TLE,MLE……)