Moving window example: calcualting slope


In [1]:
import numpy as np
import matplotlib.pyplot as plt

# Make some toy data
arr_in = np.round(np.random.uniform(low=0, high=20, size=(11,11)), 2)
arr_out=np.ones(arr_in.shape)

# Set a kernel size (e.g. value of 3 for a 3x3 window)
kernel_size=3
#stepsize=1

#~~~~~~~~~~~~~~
# Create some function to work on values within a kernel
def calc_slope(array, y, x, kernel_size):
    """
    """

    if array[(y,x)] != -9999.0:
        half_kernel = (kernel_size-1)//2
        subimg = array[(y - half_kernel):(y + half_kernel + 1), (x - half_kernel):(x + half_kernel + 1)]
        assert subimg.shape == (kernel_size, kernel_size), "Subimage dimensions not equal to kernel - you're probably at an edge - add padding to you array"       
        
        # Do something with the subimg (the extracted kernel)       
        slp_subimg=101
        return(slp_subimg)
        
    else:
        print("Move to next point")

In [2]:
print("Array before padding")
print(arr_in.shape)
plt.imshow(arr_in)


Array before padding
(11, 11)
Out[2]:
<matplotlib.image.AxesImage at 0x14c6bea6f28>

In [3]:
#~~~~~~~~~~~~~~
# Pad image to a width of (kernel size -1) /2
# Essential as the moving window needs to operate on your array corners
arr_proc=np.pad(arr_in, int((kernel_size-1)/2), mode='constant', constant_values=-9999)
print("Array after padding")
plt.imshow(arr_proc)
print(arr_proc.shape)


Array after padding
(13, 13)

In [4]:
stepsize=1
for out_i, ii in enumerate(range(0,arr_proc.shape[0]-1, stepsize)): # y       
    for out_j, jj in enumerate(range(0, arr_proc.shape[1]-1, stepsize)): # x
        print(out_i, out_j)
        arr_out[out_i, out_j] = arr_in[out_i, out_j]


        arr_out[out_i, out_j] = arr_in[out_i, out_j]
        arr_out[out_i, out_j] = calc_slope(arr_in, ii, jj, kernel_size)


0 0
---------------------------------------------------------------------------
AssertionError                            Traceback (most recent call last)
<ipython-input-4-512e27f86155> in <module>()
      7 
      8         arr_out[out_i, out_j] = arr_in[out_i, out_j]
----> 9         arr_out[out_i, out_j] = calc_slope(arr_in, ii, jj, kernel_size)

<ipython-input-1-e2906e614f0e> in calc_slope(array, y, x, kernel_size)
     19         half_kernel = (kernel_size-1)//2
     20         subimg = array[(y - half_kernel):(y + half_kernel + 1), (x - half_kernel):(x + half_kernel + 1)]
---> 21         assert subimg.shape == (kernel_size, kernel_size), "Subimage dimensions not equal to kernel - you're probably at an edge - add padding to you array"
     22 
     23         # Do something with the subimg (the extracted kernel)

AssertionError: Subimage dimensions not equal to kernel - you're probably at an edge - add padding to you array

In [5]:
# Plot output      
f, (ax1, ax2) = plt.subplots(1, 2, sharey=False)
ax1.imshow(arr_in)
ax1.set_title("Input")
ax2.imshow(arr_out)
ax2.set_title("Output")
plt.show()