아마존 본사 입사 문제였습니다.
tic-tac-toe는 두 명의 플레이어가 턴을 돌아가면서 1부터 9까지 포지션을 선택하는 게임 입니다. 선택된 포지션은 X나 0로 표시가 되며, 선택된 포지션은 다시 선택할 수가 없습니다. 게임 그리드는 3*3으로 다음과 같습니다.
* *
1 * 2 * 3
* *
* *
4 * 5 * 6
* *
* *
7 * 8 * 9
* *
가로 세로 대각선으로 먼저 세 줄을 연속으로 만드는 플레이어가 우승하게 되며 무승부인 경우도 생깁니다. (매 턴마다 포지션을 입력해야 하지만, 출력은 게임이 끝이 났을 때만 하셔도 됩니다)
입력의 예:
Player 1 - please type a position (available position(s) are 1,2,3,4,5,6,7,8,9):
출력의 예:
* *
X * X * 0
* *
* *
X * 0 * 6
* *
* *
X * 8 * 9
* *
Win playear is: player 1
Ruby
made = ->u { %w(123 456 789 147 258 369 159 357).any? {|e| (e.chars&u)[2] } }
prt = ->w,m { puts "[Winner: #{w}]", m.each_slice(3).map {|row| row*" " } }
play = ->p1=[],p2=[],map=[*1..9],n=gets.chop do
map[n.to_i-1] = (p1|p2).size.odd? ? (p2<<n; "X") : (p1<<n; "O")
winner = made[p1]? "P1" : made[p2]? "P2" : ("None" if (p1+p2)[8])
winner ? prt[winner,map] : play[p1,p2,map]
end
Test
expect_p1_win = "[Winner: P1]\n" +
"O 2 3\n" +
"X O 6\n" +
"7 X O\n"
expect_p2_win = "[Winner: P2]\n" +
"O O X\n" +
"4 X X\n" +
"X O O\n"
expect_draw = "[Winner: None]\n" +
"X O O\n" +
"O O X\n" +
"X X O\n"
test_data = ->p1,p2 { StringIO.new(p1.zip(p2).flatten*"\n") } # for stdin
# case : P1 Win
$stdin = test_data[[9,5,1], [4,8]]
expect{ play[] }.to output( expect_p1_win ).to_stdout
# case : P2 Win
$stdin = test_data[[1,2,9,8,4], [3,6,7,5]]
expect{ play[] }.to output( expect_p2_win ).to_stdout
# case : draw
$stdin = test_data[[4,5,9,2,3], [8,7,6,1]]
expect{ play[] }.to output( expect_draw ).to_stdout
2016年04月02日 03:32
풀이 작성