2011/01/26

ROT13とROT47をRubyで書いてみた

今日のRubyは単換字式暗号の一種であるROT13とROT47に挑戦しました。

ROT13 - Wikipedia

クラシカルな推理小説でよく使われる暗号の一種です。ちょっとした頭の体操気分で挑戦したのですが、意外と時間かかりました...やっぱもっとプログラムに書き慣れるように努力しよう。
これを短くする手段も検討してみようと思います。

def rot13(str)
  if /^[\sA-Za-z]+$/ =~ str then
    rstr = "[ROT13] "
    str.split(//).each do |s|
      if /\s/ =~ s then rstr.concat(s); next end
      if /[A-Z]/ == s
        s[0]+13>90? c=s[0]+13-90+65-1 : c=s[0]+13
      else
        s[0]+13>122? c=s[0]+13-122+97-1 : c=s[0]+13
      end
      rstr.concat(c.chr)
    end
    return rstr
  else
    return "[ROT13] String hasn't changed."
  end
end

# ROT47
def rot47(str)
  if /^[\s!-~]+$/ =~ str then
    rstr = "[ROT47] "
    str.split(//).each do |s|
      if /\s/ =~ s then rstr.concat(s); next end
      s[0]+47>126? c=s[0]+47-126+33-1 : c=s[0]+47
      rstr.concat(c.chr)
    end
    return rstr
  else
    return "[ROT47] String hasn't changed."
  end
end

# EXEC
while line = STDIN.gets
  if /exit/ =~ line then
     break;
  end
  line.chop!
  puts rot13(line)
  puts rot47(line)
end