def blockshaped(arr, nrows, ncols):
    """
    Return an array of shape (n, nrows, ncols) where
    n * nrows * ncols = arr.size

    If arr is a 2D array, the returned array looks like n subblocks with
    each subblock preserving the "physical" layout of arr.
    """
    h, w = arr.shape
    return arr.reshape(h // nrows, nrows, -1, ncols).swapaxes(1, 2).reshape(
        -1, nrows, ncols)
