Q:

Selecting (n-1)D array from (n)D array in numpy

Lets take a 3D array as an example. Or a cube for easier visualizing.
I want to select all the faces of that cube. And I would like to generalize this to arbitrary dimensions.
I'd also like to then add/remove faces to the cube(cuboid), and the generalization to arbitrary dimensions.
I know that for every fixed number of dimensions you can do array[:,:,0], array[-1,:,:] I'd like to know how to generalize to arbitrary dimensions and how to easily iterate over all faces.

A:

To get a face:
def get_face(M, dim, front_side):
    if front_side:
        side = 0
    else:
        side = -1
    index = tuple(side if i == dim else slice(None) for i in range(M.ndim))
    return M[index]

To add a face (untested):
def add_face(M, new_face, dim, front_side):
    #assume sizes match up correctly
    if front_side:
        return np.concatenate((new_face, M), dim)
    else:
        return np.concatenate((M, new_face), dim)

To remove a face:
def remove_face(M, dim, front_side):
    if front_side:
        dim_slice = slice(1, None)
    else:
        dim_slice = slice(None, -1)
    index = tuple(dim_slice if i == dim else slice(None) for i in range(M.ndim))
    return M[index]

Iterate over all faces:
def iter_faces(M):
    for dim in range(M.ndim):
        for front_side in (True, False):
            yield get_face(M, dim, front_side)

Some quick tests:
In [18]: M = np.arange(27).reshape((3,3,3))
In [19]: for face in iter_faces(M): print face
[[0 1 2]
 [3 4 5]
 [6 7 8]]
[[18 19 20]
 [21 22 23]
 [24 25 26]]
[[ 0  1  2]
 [ 9 10 11]
 [18 19 20]]
[[ 6  7  8]
 [15 16 17]
 [24 25 26]]
[[ 0  3  6]
 [ 9 12 15]
 [18 21 24]]
[[ 2  5  8]
 [11 14 17]
 [20 23 26]]

