私自身が表題の問題を解いた時のプログラムについて解説します。
問題の詳細は「◆小説発売記念問題◆【夏のミステリー】殺人現場のコード」(CodeIQ)を参照してください。
問題
殺人現場にプログラマが倒れていて、途中までプログラムが書かれている。
「続きを書いて欲しい」
これはダイイングメッセージなのか?
どうやらプログラムは、暗号を解き明かして、連続殺人犯の名前を出力するようだ。
暗号は各行、小文字のアルファベットで表されており、aを2の1乗、bを2の2乗、cを2の3乗……の2進数として、その文字列を結合したものだ。
各行の暗号を解き明かして、連続殺人犯の名前を出力しよう。
// 入力例
100000000000000000000100000000100000
100010100000000000000000000
// 出力例
the
cat
// 途中まで書かれたコード JavaScript (Node.js)
process.stdin.resume();
process.stdin.setEncoding('utf8');
process.stdin.on('data', function (chunk) {
var lines = chunk.toString().split('\n');
lines.forEach(function(line) {
var arr = line.match(/■■■■/g);
if (arr === null) return;
var res = arr.map(function(x) {
return ■■■■;
}).join('');
process.stdout.write(res + '\n');
});
});
Rubyで解答しています。
#!/usr/bin/ruby def solve(line) arr = line.split("1") arr.shift str = "" for a in arr str += (0x60 + a.size).chr end return str end while line = gets line.strip! next if line.empty? puts solve(line) end
問題文のプログラムは全く無視してしまいました。
入力値を1行ずつsolve()に渡して結果の文字列を印字します。
入力値を'1'で分割します。0だけの文字列の配列ができます。
先頭が1なので最初の要素は空文字列になるのでそれを捨てます(5行目)。
0の数はaは1、bは2、…と1ずつ増えてゆくので0x60に0の数を足した値がそのアルファベットの文字コードになります。それを繋げてやれば良いだけです。
問題文のコードは無視しましたが、やっていることは同じですね。
正規表現は「1(0+)」だと思うけど。最短マッチにする必要はないよね。