def trigsimp(expr, **opts):
    """
    reduces expression by using known trig identities

    Notes
    =====

    method:
    - Determine the method to use. Valid choices are 'matching' (default),
    'groebner', 'combined', and 'fu'. If 'matching', simplify the
    expression recursively by targeting common patterns. If 'groebner', apply
    an experimental groebner basis algorithm. In this case further options
    are forwarded to ``trigsimp_groebner``, please refer to its docstring.
    If 'combined', first run the groebner basis algorithm with small
    default parameters, then run the 'matching' algorithm. 'fu' runs the
    collection of trigonometric transformations described by Fu, et al.
    (see the `fu` docstring).


    Examples
    ========

    >>> from sympy import trigsimp, sin, cos, log
    >>> from sympy.abc import x, y
    >>> e = 2*sin(x)**2 + 2*cos(x)**2
    >>> trigsimp(e)
    2

    Simplification occurs wherever trigonometric functions are located.

    >>> trigsimp(log(e))
    log(2)

    Using `method="groebner"` (or `"combined"`) might lead to greater
    simplification.

    The old trigsimp routine can be accessed as with method 'old'.

    >>> from sympy import coth, tanh
    >>> t = 3*tanh(x)**7 - 2/coth(x)**7
    >>> trigsimp(t, method='old') == t
    True
    >>> trigsimp(t)
    tanh(x)**7

    """
    from sympy.simplify.fu import fu

    expr = sympify(expr)

    try:
        return expr._eval_trigsimp(**opts)
    except __HOLE__:
        pass

    old = opts.pop('old', False)
    if not old:
        opts.pop('deep', None)
        recursive = opts.pop('recursive', None)
        method = opts.pop('method', 'matching')
    else:
        method = 'old'

    def groebnersimp(ex, **opts):
        def traverse(e):
            if e.is_Atom:
                return e
            args = [traverse(x) for x in e.args]
            if e.is_Function or e.is_Pow:
                args = [trigsimp_groebner(x, **opts) for x in args]
            return e.func(*args)
        new = traverse(ex)
        if not isinstance(new, Expr):
            return new
        return trigsimp_groebner(new, **opts)

    trigsimpfunc = {
        'fu': (lambda x: fu(x, **opts)),
        'matching': (lambda x: futrig(x)),
        'groebner': (lambda x: groebnersimp(x, **opts)),
        'combined': (lambda x: futrig(groebnersimp(x,
                               polynomial=True, hints=[2, tan]))),
        'old': lambda x: trigsimp_old(x, **opts),
                   }[method]

    return trigsimpfunc(expr)
dataset/ETHPy150Open sympy/sympy/sympy/simplify/trigsimp.py/trigsimp