Skip to content

Commit

Permalink
Merge pull request #747 from polyadic/cartesian-product-docs
Browse files Browse the repository at this point in the history
Update Out-of-date Cartesian Product Docs
  • Loading branch information
bash authored Sep 11, 2023
2 parents 292d5d5 + f21f35c commit 79d8f9b
Showing 1 changed file with 40 additions and 17 deletions.
57 changes: 40 additions & 17 deletions Documentation/src/enumerable-extensions/cartesian-product.md
Original file line number Diff line number Diff line change
@@ -1,38 +1,61 @@
## CartesianProduct

In mathematics, specifically set theory, the Cartesian product of two sets A and B, denoted AΓ—B, is the set of all ordered pairs (a, b) where a is in A and b is in B.
In mathematics, specifically set theory, the Cartesian product of two sets A and B, denoted AΓ—B,
is the set of all ordered pairs (a, b) where a ∈ A and b ∈ B.

The CartesianProduct extension function returns all possible pairs of two given IEnumerables.

There are two overloads, one which lets you choose
In other words: The Cartesian product produces all possible pairs of two given `IEnumerable`s.

![cartesian-product with marbles](cartesian-product.svg "Marble me!")

### Recipe
The Cartesian product can be easily implemented ad-hoc using LINQ's built-in `SelectMany` extension function:

```cs
using System;
using System.Linq;

// Version A: Get each pair as a tuple
var result = sequenceA.SelectMany(_ => sequenceB, ValueTuple.Create);

// Version B: Transform each pair using a selector
var result = sequenceA.SelectMany(_ => sequenceB, (a, b) => ...);

// Version C: Using LINQs declarative query syntax
var result =
from a in sequenceA
from b in sequenceB
select ...;
```


### Examples

Two sequences as input:

```
```
smiles = [πŸ˜€, 😐, πŸ™„]
fruits = [πŸ‰, 🍌, πŸ‡, πŸ“]
```
```

The cartesian products of smiles and fruits:
The Cartesian products of smiles and fruits:

```
smiles Γ— fruits => [[πŸ˜€, πŸ‰], [πŸ˜€, 🍌], [πŸ˜€, πŸ‡], [πŸ˜€, πŸ“],
[😐, πŸ‰], [😐, 🍌], [😐, πŸ‡], [😐, πŸ“],
```
smiles Γ— fruits => [[πŸ˜€, πŸ‰], [πŸ˜€, 🍌], [πŸ˜€, πŸ‡], [πŸ˜€, πŸ“],
[😐, πŸ‰], [😐, 🍌], [😐, πŸ‡], [😐, πŸ“],
[πŸ™„, πŸ‰], [πŸ™„, 🍌], [πŸ™„, πŸ‡], [πŸ™„, πŸ“]]
```

In this C# example you see how all Playing cards are in fact a cartesian product of a suit and a value.
In this C# example you see how all playing cards are in fact a Cartesian products of a suit and a value.

This example uses the overload with our own selector, because we just want a sequence of strings.
This example uses the overload with a selector, because we just want a sequence of strings.

```cs
var suits = ImmutableList.Create("β™ ", "♣", "β™₯", "♦");
var values =
ImmutableList.Create("2", "3", "4", "5", "6", "7", "8", "9", "T", "J", "Q", "K", "A");
using System;
using System.Linq;
using Funcky;

var suits = Sequence.Return("β™ ", "♣", "β™₯", "♦");
var values = Sequence.Return("2", "3", "4", "5", "6", "7", "8", "9", "T", "J", "Q", "K", "A");

var allCards = suits.CartesianProduct(values, (suit, value) => $"{value}{suit}");
```
var deck = suits.SelectMany(_ => values, (suit, value) => $"{value}{suit}");
```

0 comments on commit 79d8f9b

Please sign in to comment.