このTopCoderの問題はこちらで見ることができる(要TopCoder登録 & 問題文は英語)。問題文について説明する。
キーボードのキー配列が入れ替えられ、ユーザは何をタイプしたか覚えようとしている。typedというスクリーン上に表示された文字列と、switches[]というキー配列の交換の様子が与えられたdecipherというメソッドを作成せよ。このメソッドは本来意図していたメッセージを返すものである。また、キー配列の交換は1度以上起きるものとする。例えば、もし誰かがAとSを交換し、SとDを交換したとすれば、Aがもともとあった場所にはDが、Dがもともとあった場所にはSが、Sがもともとあった場所にはAがあることになる。交換を表すswithches[]の各要素は"*:*という形式で表される。例えば先述の交換は{"A:S","S:D","D:A"}ということになる。なお、各要素の文字は順番が逆でも同じ結果になることに注意。
私の解答はこちら。
public class CeyKaps {
public String decipher(String typed, String[] switches) {
char[] keys = new char[26]; // 26文字のキーボードを表す配列と思っておく
for( int i=0 ; i<keys.length ; i++ ){ // 値の初期設定
keys[i] = (char)('A' + i);
}
// キーボードのボタンを交換していく
for( int i=0 ; i<switches.length ; i++ ){
char c1 = switches[i].charAt(0);
char c2 = switches[i].charAt(2);
int pos1 = searchFromKeys(keys, c1);
int pos2 = searchFromKeys(keys, c2);
swap(keys, pos1, pos2);
}
// typedの内容が実際に何になるかはkeysでわかる
StringBuilder sb = new StringBuilder();
for( int i=0 ; i<typed.length() ; i++ ){
int pos = typed.charAt(i) - 'A';
sb.append(keys[pos]);
}
return sb.toString();
}
// targetという文字のある位置を見つける。存在しないなら-1。
private int searchFromKeys(char[] keys, char target){
for( int i=0 ; i<keys.length ; i++ ){
if( target == keys[i] ) return i;
}
return -1;
}
// keysのp1とp2の要素を入れ替える
private void swap(char[] keys, int p1, int p2){
char tmp = keys[p1];
keys[p1] = keys[p2];
keys[p2] = tmp;
}
}得点は449.94/600、1回のsubmitでシステムテストクリア。提出者の正解率は約89%。テストのコードの良さで正解率が決まってしまっているような気がします。

0 件のコメント:
コメントを投稿