Message Boards

Non-transitive Grime Dice

For Christmas this year, I got myself a fun mathematical gift: a set of 10 non-transitive dice, namely Grime Dice! You can get your own set here. Behold their dicey splendor:

These dice possess the fascinating property that their winning relationships (in the sense of "winning" = "rolls a higher number > 50% of the time") are non-transitive. i.e. if die A wins against die B, and die B wins against die C, it actually does not hold, in general, that die A wins against die C. In fact, die C might win against die A!

That's pretty neat and non-intuitive by itself, but things get weirder when you roll two dice of the same color together: the word length cycle reverses, while the alphabetical cycle (almost) stays intact.

By word length (doubles): Red/Red loses to Blue/Blue loses to Olive/Olive loses to Yellow/Yellow loses to Magenta/Magenta loses to Red/Red

We can represent and compare pairs of dice as if they were each one 36-sided die, with each face corresponding to the total from a possible roll of the constituent dice. This lets us compute the odds of the word-length and alphabetical double dice cycles, too:

Plotting

It's much nicer to visualize the winning relationships between the dice, rather than just printing out the data. Mathematica has excellent plotting and visualization capabilities, so this is certainly possible.

GraphPlot is a good choice here. Its default visual output isn't very well-suited to this problem, though, so we will need to do some customization. We can take advantage of the various hooks which are exposed by the function, enabling us to specify custom graphical objects to represent the vertices and edges of the relationship graph.

The below code will create nice graph plots where the vertices are represented by appropriately-colored dice icons, and the edges point from winner -> loser and are labeled with the probability of that win.

Pretty neat! Besides various oddities with orientation and ordering, these plots are quite appealing. Exact placement of the vertices can be specified by the VertexCoordinateRules parameter to GraphPlot, but the default layout works well enough for our purposes.

More cycles

We have looked at the primary 5-color cycles using both single dice and doubles of the same color. That's just the beginning, though. For example, besides the 5-color cycles, various smaller cycles also exist:

How many of these smaller cycles exist? What about bigger cycles? And what about cycles involving doubles composed of 2 different colors? Or even cycles consisting of sets of 3 dice? We want to compute every possible cycle that can be created using the 10 dice from the set.

Our overall approach to solving this will be to generate directed graphs which encode all of the winning relationships between unique dice sets of a certain size (single dice, pairs, or triples), then search for cycles within those graphs.

It should be noted (we won't prove it here) that for Grime Dice, any pair of dice beats any single die, and any triple of dice beats any pair or single die. Thus it is indeed acceptable to split this computation up into separate buckets for single dice, pairs, and triples. There are no heterogeneous cycles with respect to number of competing dice.

Single dice

One might assume that the cycles of single dice would be the easiest to compute. In fact, single dice pose a couple of unique challenges that pairs and triples do not. Specifically, in a set of 10 dice, we could potentially find cycles up to size 10. But since we only have 5 colors, once a cycle becomes length-6 or longer we must necessarily have 2 same-color nodes in the cycle. We need to make sure to differentiate between the two copies of each color.

In order to capture the fact that we have 2 copies of each color on hand, we will use a bit of a hack. The "second" copy of each color will be represented as a combination with a special "white" die which has 1 face and always rolls 0.

(* dummy "white" die used to differentiate between
two instances of the same color die *)
white = dice["White"] = {{"White"}, {0}};
(* when plotting, just make the white die invisible *)
colors["White"] = Transparent;
(* all distinct single dice from set of 10 *)
allDice[1] =
Join[allColors, combine @@@ Tuples[{allColors, {white}}]];

To start building the actual relationship graph, we will define a couple of helper functions. The first is used to create the DirectedEdge values Mathematica consumes when Graph is called in the second function. The edges are directed from "winning di(c)e" to "losing di(c)e".

We can now generate the full graph of single dice relationships, and have Mathematica compute all cycles up to maximum size of 10. In the last step, note that we need to deduplicate the cycle list to eliminate those cycles which are unique only due to inclusion of the dummy "white" die.

We see that there are a total of 80 unique single-die cycles, with sizes ranging from 3 to 10.

Pairs of dice

Dice pairs turn out to be the simplest case.

With pairs (and above), we do not need to consider the possibility of distinct-yet-identical nodes in the cycle. Proof: Between any two identical nodes, there must be at least 2 other nodes (if there was only one node, it would be simultaneously beating and losing to identical nodes on either side), so a full cycle with identical nodes must have length at least 6 (the 2 identical nodes + 2 separating nodes on each side). When each node consists of a pair of dice, this requires at least 12 dice. Since we only have 10 dice, this is impossible.

This eliminates the need for the dummy die, as well as the de-duplication at the end.

The only additional wrinkle we need to consider is the possibility for a computed cycle to contain more than 2 dice of a particular color. Such cycles are invalid in our scenario, since we are only utilizing the 10 dice in the set. We will update our helpers and add some additional filtering to eliminate such cycles.

Triples of Dice

Triples are the largest sets we need to consider. At least 3 nodes are required to form a cycle, and if those nodes consist of 4 or more dice each, our set of 10 dice will not be sufficient.

Similarly, we need only search for cycles of length 3 here -- a cycle of 4 triples requires more dice than we have.

We start by extending our dice-combining function to handle triples, building up all such unique triples, and generating their winning relationship graph. Note that any triples where all 3 dice are the same color are invalid, and should be filtered.

From here, computing the triple cycles should be as simple as calling FindCycle again. Unfortunately, Mathematica spins (seemingly) indefinitely when one tries this. The relationship graph for triples is 30 nodes and 208 edges - not trivial, but not really that big. I'm not sure why FindCycle has trouble with it. Oddly enough, FindCycle immediately finds 1 cycle if that's all you ask for, but exhibits the hang if you ask for even just 2 cycles, let alone all of them.

So we will need to search for the 3-cycles in this graph manually. The below code does the trick.

This enables us to compute the cycles, though we do need to deduplicate them (unlike FindCycle, our manual code is not smart enough to realize the cycle A -> B -> C ->A is the same as the cycle B -> C -> A -> B).