**Advent Calendar 2021**

### | **Day 16** | **Day 17** | **Day 18** |

The gift is presented by **Walt Mankowski**. Today he is talking about his solution to **“The Weekly Challenge - 089”**. This is re-produced for **Advent Calendar 2021** from the original **post** by `Walt Mankoswki`

.

## Task #2: Magical Matrix

Write a script to display matrix as below with numbers `1 - 9`

. Please make sure numbers are used once.

```
[ a b c ]
[ d e f ]
[ g h i ]
```

So that it satisfies the following:

```
a + b + c = 15
d + e + f = 15
g + h + i = 15
a + d + g = 15
b + e + h = 15
c + f + i = 15
a + e + i = 15
c + e + g = 15
```

For this task we need to create a `3 x 3`

magic square; i.e. a matrix where each row, column, and diagonal sums to the same value. We’re restricted to the numbers `1-9`

, so the sums should all be `15`

.

This is trivial in `Matlab`

and `Octave`

since there’s a built in function to create magic squares, so all we need to do is say

```
magic(3)
```

We have to do a bit more work in `Perl`

, but fortunately there’s a simple algorithm for creating these sorts of magic squares called the `Siamese`

method. It works for any `m x m`

magic square where `m is odd`

. Here’s the algorithm:

#### 1. Start with a 1 in the middle column of the top row.

#### 2. For each subsequent number, try to move to the cell to the northeast (1 row up and 1 column right), wrapping around to the left and bottom when we reach the edge.

#### 3. If that cell is occupied, move one 1 down (wrapping around to the top if we’re on the bottom row) instead of moving to the northeast.

This is easy to do in `Perl`

, and we don’t even have to initialize the matrix.

```
my @m;
my $m = 3;
my $r = 0;
my $c = 1;
# fill in the magic square using the Siamese method
for my $i (1..9) {
$m[$r][$c] = $i;
my $r1 = ($r - 1) % $m;
my $c1 = ($c + 1) % $m;
if (defined $m[$r1][$c1]) {
$r = ($r + 1) % $m;
} else {
$r = $r1;
$c = $c1;
}
}
```

If you have any suggestion then please do share with us perlweeklychallenge@yahoo.com.