def assert_array(A, shape=None, uniform=None, ndim=None, size=None, dtype=None, kind=None):
    r""" Asserts whether the given array or sparse matrix has the given properties

    Parameters
    ----------
    A : ndarray, scipy.sparse matrix or array-like
        the array under investigation

    shape : shape, optional, default=None
        asserts if the array has the requested shape. Be careful with vectors
        because this will distinguish between row vectors (1,n), column vectors
        (n,1) and arrays (n,). If you want to be less specific, consider using
        size

    square : None | True | False
        if not None, asserts whether the array dimensions are uniform (e.g.
        square for a ndim=2 array) (True), or not uniform (False).

    size : int, optional, default=None
        asserts if the arrays has the requested number of elements

    ndim : int, optional, default=None
        asserts if the array has the requested dimension

    dtype : type, optional, default=None
        asserts if the array data has the requested data type. This check is
        strong, e.g. int and int64 are not equal. If you want a weaker check,
        consider the kind option

    kind : string, optional, default=None
        Checks if the array data is of the specified kind. Options include 'i'
        for integer types, 'f' for float types Check numpy.dtype.kind for
        possible options. An additional option is 'numeric' for either integer
        or float.

    Raises
    ------
    AssertionError
        If assertions has failed

    """
    try:
        if shape is not None:
            if not np.array_equal(np.shape(A), shape):
                raise AssertionError('Expected shape '+str(shape)+' but given array has shape '+str(np.shape(A)))
        if uniform is not None:
            shapearr = np.array(np.shape(A))
            is_uniform = np.count_nonzero(shapearr-shapearr[0]) == 0
            if uniform and not is_uniform:
                raise AssertionError('Given array is not uniform \n'+str(shapearr))
            elif not uniform and is_uniform:
                raise AssertionError('Given array is not nonuniform: \n'+str(shapearr))
        if size is not None:
            if not np.size(A) == size:
                raise AssertionError('Expected size '+str(size)+' but given array has size '+str(np.size(A)))
        if ndim is not None:
            if not ndim == np.ndim(A):
                raise AssertionError('Expected shape '+str(ndim)+' but given array has shape '+str(np.ndim(A)))
        if dtype is not None:
            # now we must create an array if we don't have one yet
            if not isinstance(A, (np.ndarray)) and not scisp.issparse(A):
                A = np.array(A)
            if not np.dtype(dtype) == A.dtype:
                raise AssertionError('Expected data type '+str(dtype)+' but given array has data type '+str(A.dtype))
        if kind is not None:
            # now we must create an array if we don't have one yet
            if not isinstance(A, (np.ndarray)) and not scisp.issparse(A):
                A = np.array(A)
            if kind == 'numeric':
                if not (A.dtype.kind == 'i' or A.dtype.kind == 'f'):
                    raise AssertionError('Expected numerical data, but given array has data kind '+str(A.dtype.kind))
            elif not A.dtype.kind == kind:
                raise AssertionError('Expected data kind '+str(kind)
                                     +' but given array has data kind '+str(A.dtype.kind))
    except Exception as ex:
        if isinstance(ex, AssertionError):
            raise ex
        else:  # other exception raised in the test code above
            print('Found exception: ',ex)
            raise AssertionError('Given argument is not an array of the expected shape or type:\n'+
                                 'arg = '+str(A)+'\ntype = '+str(type(A)))