问题描述:
小明得到了一个神奇的圆环。这个圆环由字母表组成首尾相接的环,环上有一个指针,最初指向字母a。小明每次可以顺时针或者逆时针旋转一格。例如,a顺时针旋转到z,逆时针旋转到b。小明手里有一个字符串,但是他遇上了点麻烦,所以他来请求你的帮助,问最少需要转多少次。
input:
输入一个字符串。
output:
输入一个数,代表最少需要转多少次才能得到这个字符串。
样例输入:
zeus
样例输出:
18
解题思路:
对于这个罗盘,我们要转到一个字母有两个方向,一个是顺时针,一个是逆时针,在这两个方向中,我们要选则旋转路径最少的,那么我们可以算出两个字母顺时针方向的距离和逆时针方向的距离,从中选择较小的。
对于算法实现,为了比较路径,我们可以通过map,来讲所有的字母映射成26个数字,在旋转时,比较顺时针旋转和逆时针旋转的距离,从而进行选择。
Ps:这里我选择了一种较为麻烦的处理方式,代码相对比较长,我们可以采用字符的ASCII码进行相减,来进行计算。我这里的代码仅提供一个思路,实现方式是可以进一步简化的。
代码:
#include<iostream>
#include<map>
#include<string>
#include<cmath>
using namespace std;
int main()
{
map<char,int> mm;//map映射
mm['a']=0;
mm['b']=1;
mm['c']=2;
mm['d']=3;
mm['e']=4;
mm['f']=5;
mm['g']=6;
mm['h']=7;
mm['i']=8;
mm['j']=9;
mm['k']=10;
mm['l']=11;
mm['m']=12;
mm['n']=13;
mm['o']=14;
mm['p']=15;
mm['q']=16;
mm['r']=17;
mm['s']=18;
mm['t']=19;
mm['u']=20;
mm['v']=21;
mm['w']=22;
mm['x']=23;
mm['y']=24;
mm['z']=25;
int temp=0;
int all=0;
string flag;
cin>>flag;
for(int i=0;i<flag.size();i++)
{
int tt=mm[flag[i]];
int tt1=abs(tt-temp);//计算逆时针和顺时针旋转需要的次数
int tt2=abs(26-tt1);
if(tt1>tt2) //选择较小的,更新起点
{
all=all+tt2;
temp=tt;
}
else{
all=all+tt1;
temp=tt;
}
}
cout<<all<<endl;
return 0;
}