第35次csp认证第二题
#include<iostream>
#include<map>
#include<vector>
#include<string>
using namespace std;
char trans[65];//0-25:A-Z 26-51:a-z 52-61:0-9 62:' '
int transnum[65];//由转换函数得到的从某字符开始到再次找到这个字符转换次数
map<char, int> ch2int;
int main() {
for (char ch = 'A';ch <= 'Z';ch++)
{
ch2int.insert({ ch,ch - 'A' });
}
for (char ch = 'a';ch <= 'z';ch++)
{
ch2int.insert({ ch,26+ch - 'a' });
}
for (char ch = '0';ch <= '9';ch++)
{
ch2int.insert({ ch,52+ch - '0' });
}
ch2int.insert({ ' ',62 });
//完成字符到索引数的映射
string s;
getline(cin, s);//初始字符串s
int n;//转换串个数
vector<char> start;
scanf_s("%d\n", &n);
for (int i = 0;i < n;i++)
{
string temp ;
getline(cin,temp);
start.push_back(temp[1]);
if (temp[1] == ' ')
trans[62] = temp[2];
if (temp[1] >= 'A' && temp[1] <= 'Z')
trans[temp[1] - 'A'] = temp[2];
if (temp[1] >= 'a' && temp[1] <= 'z')
trans[26+temp[1] - 'a'] = temp[2];
if (temp[1] >= '0' && temp[1] <= '9')
trans[52+temp[1] - '0'] = temp[2];
} //处理转换函数
for (int i = 0;i < n;i++)
{
for (auto it = start.begin();it != start.end();it++)
{
char ch_start = *it;
int num = 0;
while (trans[ch2int[ch_start]])
{
ch_start = trans[ch2int[ch_start]];
num++;
if (trans[ch2int[ch_start]] == *it)
{
transnum[ch2int[*it]] = num+1;
break;
}
}
}
}
int m;//查询个数
scanf_s("%d", &m);
for (int i = 0;i < m;i++)
{
string ans = s;
int q_num;//查询转换次数
cin >> q_num;
for (int j = 1;j < s.length() - 1;j++)//对s每个字符进行转换处理 (首尾的#不处理)
{
int q_num_temp = q_num;
char ch = s[j];
if (transnum[ch2int[ch]]) {
int short_q_num = q_num % transnum[ch2int[ch]];//有转换循环的字符,其转换次数取余后再计算
while (short_q_num--) {
ch = trans[ch2int[ch]];//转换
}
ans[j] = ch;
}
else {
while (q_num_temp--)
{
if(trans[ch2int[ch]])
ch = trans[ch2int[ch]];//转换
}
}
ans[j] = ch;
}
cout << ans << '\n';
}
return 0;
}
找变换的循环来减少一些字母在真正变换时的次数
用stl容器方便映射解题
注意getline与scanf、cin使用时需要对换行符进行处理!!!

查看7道真题和解析