title: How to implement maxpool: taking a maximum on sliding window on image or tensor
body: <p><strong>In short:</strong> I am looking for a simple <code>numpy</code> (maybe oneliner) implementation of <code>Maxpool</code> - maximum on a window on <code>numpy.narray</code> for all location of the window across dimensions. </p>
  
  <p><strong>In more details:</strong> I am implementing a convolutional neural network ("CNN"), one of the typical layers in such a network is <code>MaxPool</code> layer (look for example <a href="http://cs231n.github.io/convolutional-networks/" rel="nofollow noreferrer">here</a>). Writing 
  <code>y = MaxPool(x, S)</code>, <code>x</code> is an input <code>narray</code> and <code>S</code> is a parameter,  using pseudocode, the output of the <code>MaxPool</code> is given by: </p>
  
  <pre><code>     y[b,h,w,c] = max(x[b, s*h + i, s*w + j, c]) over i = 0,..., S-1; j = 0,...,S-1.
  </code></pre>
  
  <p>That is, <code>y</code> is <code>narray</code> where the value at indexes <code>b,h,w,c</code> equals the maximum  taken over the window of size <code>S x S</code> along the second and the third dimension of the input <code>x</code>,  the window "corner" is placed at the indexes <code>b,h,w,c</code>. </p>
  
  <p><strong>Some additional details:</strong> The network is implemented using <code>numpy</code>. CNN has many "layers" where output of one layer is the input to the next layer. The input to a layers are <code>numpy.narray</code>s called  "tensors". In my case tensors are  4-dimensional <code>numpy.narray</code>'s, <code>x</code>. That is <code>x.shape</code> is a tuple <code>(B,H,W,C)</code>. Each size of dimensions changes after the tensor is process by a layer, for example the input to layer <code>i= 4</code> can have size <code>B = 10, H = 24, W = 24, C = 3</code>, while the output, aka input to <code>i+1</code> layer has <code>B = 10, H = 12, W = 12, C = 5</code>. As indicated in the comments the size after application of <code>MaxPool</code> is <code>(B, H - S + 1, W - S + 1, C)</code>.  </p>
  
  <p><strong>For a concreteness:</strong> if I use </p>
  
  <pre><code>import numpy as np
  
  y = np.amax(x, axis = (1,2)) 
  </code></pre>
  
  <p>where <code>x.shape</code> is say <code>(2,3,3,4)</code> this will give me what I want but for a degenerate case where the window I am maximizing over is of the size <code>3 x 3</code>,   the size of the second and third dimension of <code>x</code>, which is not exactly what I want.</p>