Sha256: 50da5a498756f0ba95009041ccb86834d318ea383b3ca22c25e9bbaeeb5aacff

Contents?: true

Size: 1.69 KB

Versions: 327

Compression:

Stored size: 1.69 KB

Contents

defmodule Connect do
  @doc """
  Calculates the winner (if any) of a board
  using "O" as the white player
  and "X" as the black player
  """
  @spec result_for([String.t]) :: :none | :black | :white
  def result_for(board) do
    cond do
      black_wins?(board) -> :black
      white_wins?(board) -> :white
      true -> :none
    end
  end

  defp black_wins?(board) do
    board
    |> Enum.with_index
    |> Enum.any?(fn {row, index} ->
      String.first(row) == "X" && black_wins?(board, [{index, 0}])
    end)
  end

  defp black_wins?(board, [{_, y} | _ ]) when y + 1 == byte_size(hd board), do: true
  defp black_wins?(board, history = [last_loc | _ ]) do
    last_loc
    |> locs_next_to(history)
    |> Enum.filter(&( get_loc(board, &1) == "X" ))
    |> Enum.any?(&black_wins?(board, [&1 | history]))
  end

  defp white_wins?(board) do
    board
    |> hd
    |> String.graphemes
    |> Enum.with_index
    |> Enum.any?(fn {spot, index} ->
      spot == "O" && white_wins?(board, [{0, index}])
    end)
  end

  defp white_wins?(board, [{x, _} | _ ]) when x + 1 == length(board), do: true
  defp white_wins?(board, history = [last_loc | _ ]) do
    last_loc
    |> locs_next_to(history)
    |> Enum.filter(&( get_loc(board, &1) == "O" ))
    |> Enum.any?(&white_wins?(board, [&1 | history]))
  end

  defp locs_next_to({x, y}, history) do
    [
      {x, y - 1},
      {x, y + 1},
      {x + 1, y},
      {x - 1, y},
      {x + 1, y - 1},
      {x - 1, y + 1}
    ]
    |> Enum.filter(&valid_next_loc(&1, history))
  end

  defp valid_next_loc({x, y}, history) do
    x >= 0 && y >= 0 && !({x, y} in history)
  end

  defp get_loc(board, {x, y}) do
    row = Enum.at(board, x)
    row && String.at(row, y)
  end
end

Version data entries

327 entries across 327 versions & 1 rubygems

Version Path
trackler-2.2.1.109 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.108 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.107 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.106 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.105 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.104 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.103 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.102 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.101 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.100 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.99 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.98 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.97 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.96 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.95 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.94 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.93 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.92 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.91 tracks/elixir/exercises/connect/example.exs
trackler-2.2.1.90 tracks/elixir/exercises/connect/example.exs