# Neural Network Convolution Problem¶

Suppose you have a 2-D array, arr

import numpy as np

arr = np.array([
[0.15, 0.71, 0.26, -0.11, -2.03],
[0.13, 0.44, -0.11, -0.23, 0.19],
[-1.44, 0.51, 0.42, 2.58, -0.88],
[-1.18, 2.73, 2.35, 0.21, -0.29],
[-1.64, -0.37, 0.27, 0.57, 1.82]
])


and another, smaller 2-D array, filter

filter = np.array([
[0.08, 0.27, -0.24],
[-0.25, -0.11, -0.18],
[0.44, 1.87, 1.18]
])


In the context of neural networks, a convolution works by "sliding" filter over arr in row major order (left to right, top to bottom), taking the dot product between filter and the portion of arr it covers at each step.

The result of all these dot products is the following 3x3 array.

[[ 0.9   4.15  4.47]
[ 7.74  5.27  0.74]
[-1.6  -0.43  3.72]]


Now suppose arr is the following 33x33x3 array.

import numpy as np

rng = np.random.default_rng(123)
arr = rng.normal(size=(33,33,3)).round(2)

print(arr)
# [
#     [[-0.99 -0.37  1.29]
#      [ 0.19  0.92  0.58]
#      [-0.64  0.54 -0.32]
#      ...
#      [ 1.23  0.15  0.48]
#      [-0.15  1.32 -1.22]
#      [-0.3  -1.17  0.83]]
#
#     [[ 0.85 -0.52  1.66]
#      [-0.3  -1.38 -0.28]
#      [ 0.36 -0.23  2.27]
#      ...
#      [ 1.52  0.49  0.7 ]
#      [ 0.85 -0.91  0.12]
#      [ 0.15 -0.16 -1.09]]
#
#     ...
#
#     [[-0.38 -0.45  1.  ]
#      [-0.58  2.18  0.36]
#      [-0.44 -2.77  0.82]
#      ...
#      [-1.58 -0.5  -0.52]
#      [-0.86 -0.54 -0.26]
#      [ 0.23  0.81 -0.4 ]]
#
#     [[-1.98 -0.22 -0.79]
#      [-0.01 -1.47 -0.83]
#      [-0.87  0.3  -0.82]
#      ...
#      [ 1.42  0.7  -0.75]
#      [-0.81  1.68 -0.82]
#      [-0.93  0.28 -1.61]]
# ]


And let filter be the following 5x5x3 array.

filter = rng.normal(size=(5,5,3)).round(2)

print(filter)
# [
#     [[-1.47  0.74  0.58]
#      [ 0.46  2.37  0.79]
#      [ 1.15 -1.11 -0.29]
#      [-0.98  0.29  0.44]
#      [-0.44 -0.03  0.69]]
#
#     [[ 0.34  0.67 -0.11]
#      [-0.71 -1.   -0.88]
#      [ 0.61  0.49 -0.27]
#      [ 0.12 -1.56  0.11]
#      [ 0.32 -0.98  0.46]]
#
#     [[-1.03  0.58  0.08]
#      [ 0.89  0.86  1.49]
#      [-0.4   0.86 -0.29]
#      [ 0.07 -0.09 -0.87]
#      [ 0.2   1.22 -0.27]]
#
#     [[ 1.1  -2.61  1.64]
#      [-1.15  0.47  1.44]
#      [-1.45  0.39  1.37]
#      [ 0.13 -0.1   0.04]
#      [ 0.27  0.57  0.57]]
#
#     [[-0.61 -0.41  0.93]
#      [ 1.47 -0.07 -0.29]
#      [ 0.49  1.02  0.2 ]
#      [ 0.16  0.95  0.52]
#      [ 1.11  0.13 -0.17]]
# ]


Using strides of length two (1), calculate the convolution between these arrays. (The result should have shape 15x15.)

1. With strides of length two, filter slides over two columns/rows at each iteration.