2041 Unreliable Message

問題概要

英数字からなる文字列は、
Jを通ると一文字左にずれる。("aB23d"は"B23da"になる)
Cを通ると一文字右にずれる。("aB23d"は"daB23"になる)
Eを通ると左半分と右半分が入れ替わる。文字数が奇数の場合中央の文字は変化しない。(e3ac"は"ace3"に、"aB23d"は"3d2aB"になる)
Aを通ると逆順になる。("aB23d"は"d32Ba"になる)
Pを通ると数字が1足される。ただし9は0になる。
Mを通ると数字が1引かれる。ただし0は9になる。


伝言した人の並びおよび伝わった文字列が与えられるとき、元の文字列を復元せよ。

解法

昔AOJのほうで解いたことがあったような。。。


定義にしたがって文字列操作を実装する。
文字列の回転はSTLのrotateが便利。
rotate(開始位置,先頭に来る文字,終了位置)

ソースコード

char in[9],str[99];

int main()
{
	int n,l; scanf("%d",&n);
	rep(i,n)
	{
		scanf("%s%s",in,str); l=strlen(str);
		for(int j=strlen(in)-1;j>=0;j--)
		{
			if(in[j]=='J')rotate(str,str+l-1,str+l);
			else if(in[j]=='C')rotate(str,str+1,str+l);
			else if(in[j]=='E')rep(k,l/2)swap(str[k],str[(l+1)/2+k]);
			else if(in[j]=='A')reverse(str,str+l);
			else if(in[j]=='P')
			{
				rep(k,l)if(isdigit(str[k]))str[k]=str[k]=='0'?'9':str[k]-1;
			}
			else rep(k,l)if(isdigit(str[k]))str[k]=str[k]=='9'?'0':str[k]+1;
		}
		puts(str);
	}
	return 0;
}