예제 #1
0
def dot(a, b, strict=False):
    """
    Return the dot product of two 2D masked arrays a and b.

    Like the generic numpy equivalent, the product sum is over the last
    dimension of a and the second-to-last dimension of b.  If strict is True,
    masked values are propagated: if a masked value appears in a row or column,
    the whole row or column is considered masked.

    Parameters
    ----------
    strict : {boolean}
        Whether masked data are propagated (True) or set to 0 for the computation.

    Notes
    -----
    The first argument is not conjugated.

    """
    #!!!: Works only with 2D arrays. There should be a way to get it to run with higher dimension
    if strict and (a.ndim == 2) and (b.ndim == 2):
        a = mask_rows(a)
        b = mask_cols(b)
    #
    d = np.dot(filled(a, 0), filled(b, 0))
    #
    am = ~getmaskarray(a)
    bm = ~getmaskarray(b)
    m = ~np.dot(am, bm)
    return masked_array(d, mask=m)
예제 #2
0
def assert_array_compare(comparison,
                         x,
                         y,
                         err_msg='',
                         verbose=True,
                         header='',
                         fill_value=True):
    """Asserts that a comparison relation between two masked arrays is satisfied
    elementwise."""
    # Fill the data first
    xf = filled(x)
    yf = filled(y)
    # Allocate a common mask and refill
    m = mask_or(getmask(x), getmask(y))
    x = masked_array(xf, copy=False, mask=m)
    y = masked_array(yf, copy=False, mask=m)
    if ((x is masked) and not (y is masked)) or \
        ((y is masked) and not (x is masked)):
        msg = build_err_msg([x, y],
                            err_msg=err_msg,
                            verbose=verbose,
                            header=header,
                            names=('x', 'y'))
        raise ValueError(msg)
    # OK, now run the basic tests on filled versions
    return utils.assert_array_compare(comparison,
                                      x.filled(fill_value),
                                      y.filled(fill_value),
                                      err_msg=err_msg,
                                      verbose=verbose,
                                      header=header)
예제 #3
0
def dot(a,b, strict=False):
    """Return the dot product of two 2D masked arrays a and b.

    Like the generic numpy equivalent, the product sum is over the
    last dimension of a and the second-to-last dimension of b.  If
    strict is True, masked values are propagated: if a masked value
    appears in a row or column, the whole row or column is considered
    masked.

    Parameters
    ----------
        strict : {boolean}
            Whether masked data are propagated (True) or set to 0 for
            the computation.

    Notes
    -----
        The first argument is not conjugated.

    """
    #TODO: Works only with 2D arrays. There should be a way to get it to run with higher dimension
    if strict and (a.ndim == 2) and (b.ndim == 2):
        a = mask_rows(a)
        b = mask_cols(b)
    #
    d = np.dot(filled(a, 0), filled(b, 0))
    #
    am = (~getmaskarray(a))
    bm = (~getmaskarray(b))
    m = ~np.dot(am, bm)
    return masked_array(d, mask=m)
예제 #4
0
def assert_array_compare(comparison, x, y, err_msg='', header='', 
                         fill_value=True):
    """Asserts that a comparison relation between two masked arrays is satisfied
    elementwise."""
    xf = filled(x)
    yf = filled(y)
    m = mask_or(getmask(x), getmask(y))
    
    x = masked_array(xf, copy=False, subok=False, mask=m).filled(fill_value)
    y = masked_array(yf, copy=False, subok=False, mask=m).filled(fill_value)
    
    if ((x is masked) and not (y is masked)) or \
        ((y is masked) and not (x is masked)):
        msg = build_err_msg([x, y], err_msg, header=header, names=('x', 'y'))
        raise ValueError(msg)
    
    if (x.dtype.char != "O") and (x.dtype.char != "S"):
        x = x.astype(float_)
        if isinstance(x, N.ndarray) and x.size > 1:
            x[N.isnan(x)] = 0
        elif N.isnan(x):
            x = 0
    if (y.dtype.char != "O") and (y.dtype.char != "S"):
        y = y.astype(float_)
        if isinstance(y, N.ndarray) and y.size > 1:
            y[N.isnan(y)] = 0
        elif N.isnan(y):
            y = 0
    try:
        cond = (x.shape==() or y.shape==()) or x.shape == y.shape
        if not cond:
            msg = build_err_msg([x, y],
                                err_msg
                                + '\n(shapes %s, %s mismatch)' % (x.shape,
                                                                  y.shape),
                                header=header,
                                names=('x', 'y'))
            assert cond, msg
        val = comparison(x,y)
        if m is not nomask and fill_value:
            val = masked_array(val, mask=m, copy=False)
        if isinstance(val, bool):
            cond = val
            reduced = [0]
        else:
            reduced = val.ravel()
            cond = reduced.all()
            reduced = reduced.tolist()
        if not cond:
            match = 100-100.0*reduced.count(1)/len(reduced)
            msg = build_err_msg([x, y],
                                err_msg
                                + '\n(mismatch %s%%)' % (match,),
                                header=header,
                                names=('x', 'y'))
            assert cond, msg
    except ValueError:
        msg = build_err_msg([x, y], err_msg, header=header, names=('x', 'y'))
        raise ValueError(msg)
예제 #5
0
def almost(a, b, decimal=6, fill_value=True):
    """Returns True if a and b are equal up to decimal places.
If fill_value is True, masked values considered equal. Otherwise, masked values
are considered unequal.
    """
    m = mask_or(getmask(a), getmask(b))
    d1 = filled(a)
    d2 = filled(b)
    if d1.dtype.char == "O" or d2.dtype.char == "O":
        return np.equal(d1, d2).ravel()
    x = filled(masked_array(d1, copy=False, mask=m), fill_value).astype(float_)
    y = filled(masked_array(d2, copy=False, mask=m), 1).astype(float_)
    d = np.around(np.abs(x - y), decimal) <= 10.0**(-decimal)
    return d.ravel()
예제 #6
0
def almost(a, b, decimal=6, fill_value=True):
    """Returns True if a and b are equal up to decimal places.
If fill_value is True, masked values considered equal. Otherwise, masked values
are considered unequal.
    """
    m = mask_or(getmask(a), getmask(b))
    d1 = filled(a)
    d2 = filled(b)
    if d1.dtype.char == "O" or d2.dtype.char == "O":
        return N.equal(d1,d2).ravel()
    x = filled(masked_array(d1, copy=False, mask=m), fill_value).astype(float_)
    y = filled(masked_array(d2, copy=False, mask=m), 1).astype(float_)
    d = N.around(N.abs(x-y),decimal) <= 10.0**(-decimal)
    return d.ravel()
예제 #7
0
 def _median1D(data):
     counts = filled(count(data), 0)
     (idx, rmd) = divmod(counts, 2)
     if rmd:
         choice = slice(idx, idx + 1)
     else:
         choice = slice(idx - 1, idx + 1)
     return data[choice].mean(0)
예제 #8
0
 def _median1D(data):
     counts = filled(count(data, axis),0)
     (idx, rmd) = divmod(counts, 2)
     if rmd:
         choice = slice(idx, idx+1)
     else:
         choice = slice(idx-1, idx+1)
     return data[choice].mean(0)
예제 #9
0
def approx (a, b, fill_value=1, rtol=1.e-5, atol=1.e-8):
    """Returns true if all components of a and b are equal subject to given tolerances.
    If fill_value is 1, masked values considered equal.
    If fill_value is 0, masked values considered unequal.
    The relative error rtol should be positive and << 1.0
    The absolute error atol comes into play for those elements of b that are 
    very small or zero; it says how small a must be also.
    """
    m = mask_or(getmask(a), getmask(b))
    d1 = filled(a)
    d2 = filled(b)
    if d1.dtype.char == "O" or d2.dtype.char == "O":
        return N.equal(d1,d2).ravel()
    x = filled(masked_array(d1, copy=False, mask=m), fill_value).astype(float_)
    y = filled(masked_array(d2, copy=False, mask=m), 1).astype(float_)
    d = N.less_equal(umath.absolute(x-y), atol + rtol * umath.absolute(y))
    return d.ravel()
예제 #10
0
def approx(a, b, fill_value=True, rtol=1.e-5, atol=1.e-8):
    """Returns true if all components of a and b are equal subject to given tolerances.

If fill_value is True, masked values considered equal. Otherwise, masked values
are considered unequal.
The relative error rtol should be positive and << 1.0
The absolute error atol comes into play for those elements of b that are very
small or zero; it says how small a must be also.
    """
    m = mask_or(getmask(a), getmask(b))
    d1 = filled(a)
    d2 = filled(b)
    if d1.dtype.char == "O" or d2.dtype.char == "O":
        return np.equal(d1, d2).ravel()
    x = filled(masked_array(d1, copy=False, mask=m), fill_value).astype(float_)
    y = filled(masked_array(d2, copy=False, mask=m), 1).astype(float_)
    d = np.less_equal(umath.absolute(x - y), atol + rtol * umath.absolute(y))
    return d.ravel()
def assert_array_compare(comparison, x, y, err_msg='', verbose=True, header='',
                         fill_value=True):
    """Asserts that a comparison relation between two masked arrays is satisfied
    elementwise."""
    # Fill the data first
    xf = filled(x)
    yf = filled(y)
    # Allocate a common mask and refill
    m = mask_or(getmask(x), getmask(y))
    x = masked_array(xf, copy=False, mask=m)
    y = masked_array(yf, copy=False, mask=m)
    if ((x is masked) and not (y is masked)) or \
        ((y is masked) and not (x is masked)):
        msg = build_err_msg([x, y], err_msg=err_msg, verbose=verbose,
                            header=header, names=('x', 'y'))
        raise ValueError(msg)
    # OK, now run the basic tests on filled versions
    return utils.assert_array_compare(comparison,
                                x.filled(fill_value), y.filled(fill_value),
                                err_msg=err_msg,
                                verbose=verbose, header=header)
예제 #12
0
def average(a, axis=None, weights=None, returned=False):
    """
    Average the array over the given axis.

    Parameters
    ----------
    axis : {None,int}, optional
        Axis along which to perform the operation.
        If None, applies to a flattened version of the array.
    weights : {None, sequence}, optional
        Sequence of weights.
        The weights must have the shape of a, or be 1D with length
        the size of a along the given axis.
        If no weights are given, weights are assumed to be 1.
    returned : {False, True}, optional
        Flag indicating whether a tuple (result, sum of weights/counts)
        should be returned as output (True), or just the result (False).

    """
    a = asarray(a)
    mask = a.mask
    ash = a.shape
    if ash == ():
        ash = (1,)
    if axis is None:
        if mask is nomask:
            if weights is None:
                n = a.sum(axis=None)
                d = float(a.size)
            else:
                w = filled(weights, 0.0).ravel()
                n = umath.add.reduce(a._data.ravel() * w)
                d = umath.add.reduce(w)
                del w
        else:
            if weights is None:
                n = a.filled(0).sum(axis=None)
                d = umath.add.reduce((-mask).ravel().astype(int))
            else:
                w = array(filled(weights, 0.0), float, mask=mask).ravel()
                n = add.reduce(a.ravel() * w)
                d = add.reduce(w)
                del w
    else:
        if mask is nomask:
            if weights is None:
                d = ash[axis] * 1.0
                n = add.reduce(a._data, axis, dtype=float)
            else:
                w = filled(weights, 0.0)
                wsh = w.shape
                if wsh == ():
                    wsh = (1,)
                if wsh == ash:
                    w = np.array(w, float, copy=0)
                    n = add.reduce(a * w, axis)
                    d = add.reduce(w, axis)
                    del w
                elif wsh == (ash[axis],):
                    ni = ash[axis]
                    r = [None] * len(ash)
                    r[axis] = slice(None, None, 1)
                    w = eval("w[" + repr(tuple(r)) + "] * ones(ash, float)")
                    n = add.reduce(a * w, axis, dtype=float)
                    d = add.reduce(w, axis, dtype=float)
                    del w, r
                else:
                    raise ValueError, "average: weights wrong shape."
        else:
            if weights is None:
                n = add.reduce(a, axis, dtype=float)
                d = umath.add.reduce((-mask), axis=axis, dtype=float)
            else:
                w = filled(weights, 0.0)
                wsh = w.shape
                if wsh == ():
                    wsh = (1,)
                if wsh == ash:
                    w = array(w, dtype=float, mask=mask, copy=0)
                    n = add.reduce(a * w, axis, dtype=float)
                    d = add.reduce(w, axis, dtype=float)
                elif wsh == (ash[axis],):
                    ni = ash[axis]
                    r = [None] * len(ash)
                    r[axis] = slice(None, None, 1)
                    w = eval("w[" + repr(tuple(r)) + "] * masked_array(ones(ash, float), mask)")
                    n = add.reduce(a * w, axis, dtype=float)
                    d = add.reduce(w, axis, dtype=float)
                else:
                    raise ValueError, "average: weights wrong shape."
                del w
    if n is masked or d is masked:
        return masked
    result = n / d
    del n

    if isinstance(result, MaskedArray):
        if ((axis is None) or (axis == 0 and a.ndim == 1)) and (result.mask is nomask):
            result = result._data
        if returned:
            if not isinstance(d, MaskedArray):
                d = masked_array(d)
            if isinstance(d, ndarray) and (not d.shape == result.shape):
                d = ones(result.shape, dtype=float) * d
    if returned:
        return result, d
    else:
        return result
예제 #13
0
def average(a, axis=None, weights=None, returned=False):
    """Average the array over the given axis.

    Parameters
    ----------
    axis : {None,int}, optional
        Axis along which to perform the operation.
        If None, applies to a flattened version of the array.
    weights : {None, sequence}, optional
        Sequence of weights.
        The weights must have the shape of a, or be 1D with length
        the size of a along the given axis.
        If no weights are given, weights are assumed to be 1.
    returned : {False, True}, optional
        Flag indicating whether a tuple (result, sum of weights/counts)
        should be returned as output (True), or just the result (False).

    """
    a = asarray(a)
    mask = a.mask
    ash = a.shape
    if ash == ():
        ash = (1,)
    if axis is None:
        if mask is nomask:
            if weights is None:
                n = a.sum(axis=None)
                d = float(a.size)
            else:
                w = filled(weights, 0.0).ravel()
                n = umath.add.reduce(a._data.ravel() * w)
                d = umath.add.reduce(w)
                del w
        else:
            if weights is None:
                n = a.filled(0).sum(axis=None)
                d = umath.add.reduce((-mask).ravel().astype(int))
            else:
                w = array(filled(weights, 0.0), float, mask=mask).ravel()
                n = add.reduce(a.ravel() * w)
                d = add.reduce(w)
                del w
    else:
        if mask is nomask:
            if weights is None:
                d = ash[axis] * 1.0
                n = add.reduce(a._data, axis, dtype=float)
            else:
                w = filled(weights, 0.0)
                wsh = w.shape
                if wsh == ():
                    wsh = (1,)
                if wsh == ash:
                    w = np.array(w, float, copy=0)
                    n = add.reduce(a*w, axis)
                    d = add.reduce(w, axis)
                    del w
                elif wsh == (ash[axis],):
                    ni = ash[axis]
                    r = [None]*len(ash)
                    r[axis] = slice(None, None, 1)
                    w = eval ("w["+ repr(tuple(r)) + "] * ones(ash, float)")
                    n = add.reduce(a*w, axis, dtype=float)
                    d = add.reduce(w, axis, dtype=float)
                    del w, r
                else:
                    raise ValueError, 'average: weights wrong shape.'
        else:
            if weights is None:
                n = add.reduce(a, axis, dtype=float)
                d = umath.add.reduce((-mask), axis=axis, dtype=float)
            else:
                w = filled(weights, 0.0)
                wsh = w.shape
                if wsh == ():
                    wsh = (1,)
                if wsh == ash:
                    w = array(w, dtype=float, mask=mask, copy=0)
                    n = add.reduce(a*w, axis, dtype=float)
                    d = add.reduce(w, axis, dtype=float)
                elif wsh == (ash[axis],):
                    ni = ash[axis]
                    r = [None]*len(ash)
                    r[axis] = slice(None, None, 1)
                    w = eval ("w["+ repr(tuple(r)) + \
                              "] * masked_array(ones(ash, float), mask)")
                    n = add.reduce(a*w, axis, dtype=float)
                    d = add.reduce(w, axis, dtype=float)
                else:
                    raise ValueError, 'average: weights wrong shape.'
                del w
    if n is masked or d is masked:
        return masked
    result = n/d
    del n

    if isinstance(result, MaskedArray):
        if ((axis is None) or (axis==0 and a.ndim == 1)) and \
           (result.mask is nomask):
            result = result._data
        if returned:
            if not isinstance(d, MaskedArray):
                d = masked_array(d)
            if isinstance(d, ndarray) and (not d.shape == result.shape):
                d = ones(result.shape, dtype=float) * d
    if returned:
        return result, d
    else:
        return result
예제 #14
0
def assert_array_compare(comparison,
                         x,
                         y,
                         err_msg='',
                         header='',
                         fill_value=True):
    """Asserts that a comparison relation between two masked arrays is satisfied
    elementwise."""
    xf = filled(x)
    yf = filled(y)
    m = mask_or(getmask(x), getmask(y))

    x = masked_array(xf, copy=False, subok=False, mask=m).filled(fill_value)
    y = masked_array(yf, copy=False, subok=False, mask=m).filled(fill_value)

    if ((x is masked) and not (y is masked)) or \
        ((y is masked) and not (x is masked)):
        msg = build_err_msg([x, y], err_msg, header=header, names=('x', 'y'))
        raise ValueError(msg)

    if (x.dtype.char != "O") and (x.dtype.char != "S"):
        x = x.astype(float_)
        if isinstance(x, N.ndarray) and x.size > 1:
            x[N.isnan(x)] = 0
        elif N.isnan(x):
            x = 0
    if (y.dtype.char != "O") and (y.dtype.char != "S"):
        y = y.astype(float_)
        if isinstance(y, N.ndarray) and y.size > 1:
            y[N.isnan(y)] = 0
        elif N.isnan(y):
            y = 0
    try:
        cond = (x.shape == () or y.shape == ()) or x.shape == y.shape
        if not cond:
            msg = build_err_msg([x, y],
                                err_msg + '\n(shapes %s, %s mismatch)' %
                                (x.shape, y.shape),
                                header=header,
                                names=('x', 'y'))
            assert cond, msg
        val = comparison(x, y)
        if m is not nomask and fill_value:
            val = masked_array(val, mask=m, copy=False)
        if isinstance(val, bool):
            cond = val
            reduced = [0]
        else:
            reduced = val.ravel()
            cond = reduced.all()
            reduced = reduced.tolist()
        if not cond:
            match = 100 - 100.0 * reduced.count(1) / len(reduced)
            msg = build_err_msg([x, y],
                                err_msg + '\n(mismatch %s%%)' % (match, ),
                                header=header,
                                names=('x', 'y'))
            assert cond, msg
    except ValueError:
        msg = build_err_msg([x, y], err_msg, header=header, names=('x', 'y'))
        raise ValueError(msg)