题解:P1079 [NOIP2012 提高组] Vigenère 密码
wangzhihong10002 · · 题解
传送门。
题目分析:
\
观察图片我们可以发现密钥每往后移一位整个字母表就往前移一位。所以我们可以得出一个公式
分析完了,那该怎么实现呢?\ 这里给出代码:
#include<bits/stdc++.h>
using namespace std;
string m,k;
int sum=0;
char s;//为当前字母的密文。
int main(){
cin>>k>>m;
for(int i=0;i<k.size();i++)if(k[i]>='a'&&k[i]<='z')k[i]-=32;//将密钥统一转化为大写字母,这样好算些。
for(int i=0;i<m.size();i++){
if(m[i]>='A'&&m[i]<='Z'){//分类讨论,当明文为大写字母时。
if(m[i]-(k[sum]-'A')>='A'&&m[i]-(k[sum]-'A')<='Z')s=m[i]-(k[sum]-'A');//还记得公式吗?
else s=char('Z'-('A'-(m[i]-(k[sum]-'A')))+1);
}
else{//当明文为小写字母时。
if(m[i]-(k[sum]-'A')<='z'&&m[i]-(k[sum]-'A')>='a')s=m[i]-(k[sum]-'A');
else s=char('z'-('a'-(m[i]-(k[sum]-'A')))+1);
}
cout<<s;//输出密文。
sum++;//密钥往后移一位。
if(sum==k.size()){//判断:当密钥移到最后一位时就从头开始。
sum=0;
}
}
return 0;//华丽结束。
}
我的 AC 记录,未吸氧。