「ソフトウェアエンジニアならば1時間以内に解けなければいけない5つの問題」をRubyで

ちょっと、というか結構古いけど 「ソフトウェアエンジニアならば1時間以内に解けなければいけない5つの問題」 というのを見つけた。

 cf. 1時間以内に解けなければプログラマ失格となってしまう5つの問題が話題に – SOFTANTENNA BLOG

大元のページはもうなくなっているようだけど、上のページに問題が載っているので Ruby でやってみた。

問題1

forループ、whileループ、および再帰を使用して、リスト内の数字の合計を計算する3つの関数を記述せよ。

def solv1(ary)
  result = 0
  for i in ary
    result += i
  end
  result
end

def solv2(ary)
  result = 0
  while ary.size > 0
    result += ary.shift
  end
  result
end

def solv3(ary)
  if ary.empty?
    0
  else
    x = ary.shift
    x + solv3(ary)
  end
end

puts solv1([1,2,3,4,5])
puts solv2([1,2,3,4,5])
puts solv3([1,2,3,4,5])

問題2

交互に要素を取ることで、2つのリストを結合する関数を記述せよ。例えば [a, b, c]と[1, 2, 3]という2つのリストを与えると、関数は [a, 1, b, 2, c, 3]を返す。

def solv(a1, a2)
  result = []
  until a1.empty?
    result << a1.shift
    result << a2.shift
  end
  result
end

p solv(['a', 'b', 'c'], [1, 2, 3])

問題3

最初の100個のフィボナッチ数のリストを計算する関数を記述せよ。定義では、フィボナッチ数列の最初の2つの数字は0と1で、次の数は前の2つの合計となる。例えば最初の10個のフィボナッチ数列は、0, 1, 1, 2, 3, 5, 8, 13, 21, 34となる。

require 'pp'

def fib(a, b, acc, n)
  if n == 0
    acc
  else
    acc << a
    fib(b, a + b, acc, n - 1)
  end
end

def solv
  fib(0, 1, [], 100)
end

pp solv

問題4

正の整数のリストを与えられたとき、数を並び替えて可能な最大数を返す関数を記述せよ。例えば、[50, 2, 1, 9]が与えられた時、95021が答えとなる。

def solv(ary)
  ary.map{|x| x.to_s }.sort.reverse.join("").to_i
end

puts solv([50, 2, 1, 9])

問題5

1,2,…,9の数をこの順序で、”+”、”-“、またはななにもせず結果が100となるあらゆる組合せを出力するプログラムを記述せよ。例えば、1 + 2 + 34 – 5 + 67 – 8 + 9 = 100となる 。

def combi(ary)
  if ary.size == 1
    ary
  else
    result = []
    x = ary.shift
    c = combi(ary)
    ["+", "-", ""].each do |op|
      result += c.map{|e| x + op + e }
    end
    result
  end
end

def solv
  a = [1,2,3,4,5,6,7,8,9].map{|n| n.to_s }
  result = []
  combi(a).each do |e|
    if eval(e) == 100
      result << e
    end
  end
  result
end

solv.each do |e|
  puts e + " = 100"
end

俺はソフトウェアエンジニアじゃないけど、どうにか1時間以内に5問ともできた。一番難しかったのは問題5だけど、意外にてこずったのは問題1。Ruby の for の使い方(というか for があること自体)を忘れていて、結局ここだけググった。