Here is a simple game for two players which you might like to play at your next Haskell meetup.

### Setup

First, the two players agree on an algebraic data type, expressible in Haskell. Recursive types tend to work best.

For example, we might choose the type of `[()]`

of lists of elements of type `()`

.

### Gameplay

The goal is to write an exhaustive function `f`

from the chosen type to `()`

, by pattern matching. The return type isn't important, so I use `()`

here arbitrarily.

So the players agree on the type signature:

```
f :: [()] -> ()
```

Player one goes first, and writes down the first line of the function, which consists of a pattern recognizing some subset of the values of the chosen type.

For example, player one might choose the following:

```
f (_ : _ : _) = ()
```

Notice that the only thing which is important here is the pattern itself.

Player two goes next, but there is an additional rule - a player cannot introduce a *redundant pattern*. For example, it would be an illegal move for player two to write down the pattern `(_ : _ : _ : _)`

at this point, since that pattern doesn't match any new values.

Play continues in this way, and the last player to write down a non-redundant pattern loses.

So, for example, player two might legally write down the next line as:

```
f [] = ()
```

forcing player one to cover the only remaining case:

```
f [_] = ()
```

and so player two would win.

### Explanation

This game is an example of a poset game, where the poset is given by the choice of type. It generalizes Nim, since choosing an N-ary sum of natural numbers recovers a game of Nim with N heaps.

It is possible for gameplay to go on indefinitely. For example, in the game above, the players could alternately choose patterns matching lists of increasing fixed length: `[]`

, `[_]`

, `[_, _]`

, ..., and the function would never become exhaustive. However, it is possible to force a finite game by choosing a pattern which matches a cofinite number of values.

Try it and let me know what you think!