Exemplo n.º 1
0
def fsum(terms):
    """
    Calculates a sum containing a finite number of terms (for infinite
    series, see :func:`nsum`). The terms will be converted to
    mpmath numbers. For len(terms) > 2, this function is generally
    faster and produces more accurate results than the builtin
    Python function :func:`sum`.

        >>> from sympy.mpmath import *
        >>> mp.dps = 15
        >>> fsum([1, 2, 0.5, 7])
        mpf('10.5')
    """
    prec, rnd = prec_rounding
    real = []
    imag = []
    other = 0
    for term in terms:
        if hasattr(term, "_mpf_"):
            val = term._mpf_
        elif hasattr(term, "_mpc_"):
            val, im = term._mpc_
            imag.append(im)
        else:
            term = mpmathify(term)
            if hasattr(term, "_mpf_"):
                val = term._mpf_
            elif hasattr(term, "_mpc_"):
                val, im = term._mpc_
                imag.append(im)
            else:
                other += term
                continue
        real.append(val)
    s = mpf_sum(real, prec, rnd)
    if imag:
        s = make_mpc((s, mpf_sum(imag, prec, rnd)))
    else:
        s = make_mpf(s)
    if other is 0:
        return s
    else:
        return s + other
Exemplo n.º 2
0
def fdot(A, B=None):
    r"""
    Computes the dot product of the iterables `A` and `B`,

    .. math ::

        \sum_{k=0} A_k B_k.

    Alternatively, :func:`fdot` accepts a single iterable of pairs.
    In other words, ``fdot(A,B)`` and ``fdot(zip(A,B))`` are equivalent.

    The elements are automatically converted to mpmath numbers.

    Examples::

        >>> from sympy.mpmath import *
        >>> mp.dps = 15
        >>> A = [2, 1.5, 3]
        >>> B = [1, -1, 2]
        >>> fdot(A, B)
        mpf('6.5')
        >>> zip(A, B)
        [(2, 1), (1.5, -1), (3, 2)]
        >>> fdot(_)
        mpf('6.5')

    """
    if B:
        A = zip(A, B)
    prec, rnd = prec_rounding
    real = []
    imag = []
    other = 0
    hasattr_ = hasattr
    types = (mpf, mpc)
    for a, b in A:
        if type(a) not in types: a = mpmathify(a)
        if type(b) not in types: b = mpmathify(b)
        a_real = hasattr_(a, "_mpf_")
        b_real = hasattr_(b, "_mpf_")
        if a_real and b_real:
            real.append(mpf_mul(a._mpf_, b._mpf_))
            continue
        a_complex = hasattr_(a, "_mpc_")
        b_complex = hasattr_(b, "_mpc_")
        if a_real and b_complex:
            aval = a._mpf_
            bre, bim = b._mpc_
            real.append(mpf_mul(aval, bre))
            imag.append(mpf_mul(aval, bim))
        elif b_real and a_complex:
            are, aim = a._mpc_
            bval = b._mpf_
            real.append(mpf_mul(are, bval))
            imag.append(mpf_mul(aim, bval))
        elif a_complex and b_complex:
            re, im = mpc_mul(a._mpc_, b._mpc_, prec+20)
            real.append(re)
            imag.append(im)
        else:
            other += a*b
    s = mpf_sum(real, prec, rnd)
    if imag:
        s = make_mpc((s, mpf_sum(imag, prec, rnd)))
    else:
        s = make_mpf(s)
    if other is 0:
        return s
    else:
        return s + other