Repository: vaskoz/dailycodingproblem-go (go)

Issue:
Day 468
Good morning! Here's your coding interview problem for today.

This problem was asked by Facebook.

Given an `N` by `N` matrix, rotate it by 90 degrees clockwise.

For example, given the following matrix:
```
[[1, 2, 3],
 [4, 5, 6],
 [7, 8, 9]]
```
you should return:
```
[[7, 4, 1],
 [8, 5, 2],
 [9, 6, 3]]
```
Follow-up: What if you couldn't use any extra space?

Pull request description:
Day468
Resolves #949.

Patch:
diff --git a/README.md b/README.md
index 02c0def..1feecb5 100644
--- a/README.md
+++ b/README.md
@@ -462,6 +462,7 @@ problems from
 * [Day 463](https://github.com/vaskoz/dailycodingproblem-go/issues/937)
 * [Day 464](https://github.com/vaskoz/dailycodingproblem-go/issues/935)
 * [Day 465](https://github.com/vaskoz/dailycodingproblem-go/issues/933)
+* [Day 468](https://github.com/vaskoz/dailycodingproblem-go/issues/949)
 * [Day 469](https://github.com/vaskoz/dailycodingproblem-go/issues/947)
 * [Day 470](https://github.com/vaskoz/dailycodingproblem-go/issues/945)
 * [Day 471](https://github.com/vaskoz/dailycodingproblem-go/issues/943)
diff --git a/day468/problem.go b/day468/problem.go
new file mode 100644
index 0000000..7f89446
--- /dev/null
+++ b/day468/problem.go
@@ -0,0 +1,36 @@
+package day468
+
+// Matrix is a 2D array of integers of NxN dimension.
+type Matrix [][]int
+
+// RotateMatrixRightClockwise90 does what it says.
+// It creates a new Matrix for the result.
+func RotateMatrixRightClockwise90(m Matrix) Matrix {
+	result := make(Matrix, len(m))
+	for i := range result {
+		result[i] = make([]int, len(m))
+	}
+
+	for i := range m {
+		for j := range m[i] {
+			result[j][len(m)-1-i] = m[i][j]
+		}
+	}
+
+	return result
+}
+
+// RotateMatrixRightClockwise90InPlace does what it says.
+func RotateMatrixRightClockwise90InPlace(m Matrix) {
+	n := len(m)
+
+	for i := 0; i < n/2; i++ {
+		for j := i; j < n-i-1; j++ {
+			var next int
+			next, m[j][n-i-1] = m[j][n-i-1], m[i][j]      // right-side
+			next, m[n-i-1][n-j-1] = m[n-i-1][n-j-1], next // bottom-side
+			next, m[n-j-1][i] = m[n-j-1][i], next         // left-side
+			m[i][j] = next                                // top-side
+		}
+	}
+}


Test patch:
diff --git a/day468/problem_test.go b/day468/problem_test.go
new file mode 100644
index 0000000..188b0bf
--- /dev/null
+++ b/day468/problem_test.go
@@ -0,0 +1,96 @@
+package day468
+
+import (
+	"reflect"
+	"testing"
+)
+
+// nolint
+var testcases = []struct {
+	matrix, rotated Matrix
+}{
+	{Matrix{
+		{1, 2, 3},
+		{4, 5, 6},
+		{7, 8, 9},
+	}, Matrix{
+		{7, 4, 1},
+		{8, 5, 2},
+		{9, 6, 3},
+	}},
+	{Matrix{
+		{1, 2, 3, 4},
+		{5, 6, 7, 8},
+		{9, 10, 11, 12},
+		{13, 14, 15, 16},
+	}, Matrix{
+		{13, 9, 5, 1},
+		{14, 10, 6, 2},
+		{15, 11, 7, 3},
+		{16, 12, 8, 4},
+	}},
+	{Matrix{
+		{1, 2, 3, 4, 5},
+		{6, 7, 8, 9, 10},
+		{11, 12, 13, 14, 15},
+		{16, 17, 18, 19, 20},
+		{21, 22, 23, 24, 25},
+	}, Matrix{
+		{21, 16, 11, 6, 1},
+		{22, 17, 12, 7, 2},
+		{23, 18, 13, 8, 3},
+		{24, 19, 14, 9, 4},
+		{25, 20, 15, 10, 5},
+	}},
+}
+
+func TestRotateMatrixRightClockwise90(t *testing.T) {
+	t.Parallel()
+
+	for _, tc := range testcases {
+		if result := RotateMatrixRightClockwise90(tc.matrix); !reflect.DeepEqual(result, tc.rotated) {
+			t.Errorf("Expected %v got %v", tc.rotated, result)
+		}
+	}
+}
+
+func BenchmarkRotateMatrixRightClockwise90(b *testing.B) {
+	for i := 0; i < b.N; i++ {
+		for _, tc := range testcases {
+			RotateMatrixRightClockwise90(tc.matrix)
+		}
+	}
+}
+
+func TestRotateMatrixRightClockwise90InPlace(t *testing.T) {
+	t.Parallel()
+
+	for _, tc := range testcases {
+		copied := copyMatrix(tc.matrix)
+		RotateMatrixRightClockwise90InPlace(copied)
+
+		if !reflect.DeepEqual(copied, tc.rotated) {
+			t.Errorf("Expected %v got %v", tc.rotated, copied)
+		}
+	}
+}
+
+func BenchmarkRotateMatrixRightClockwise90InPlace(b *testing.B) {
+	for i := 0; i < b.N; i++ {
+		for _, tc := range testcases {
+			copied := copyMatrix(tc.matrix)
+			RotateMatrixRightClockwise90InPlace(copied)
+		}
+	}
+}
+
+func copyMatrix(m Matrix) Matrix {
+	copied := make(Matrix, len(m))
+
+	for i := range m {
+		copied[i] = make([]int, len(m))
+		copy(copied[i], m[i])
+	}
+
+	return copied
+}