コード例 #1
0
ファイル: test_fancysets.py プロジェクト: AStorus/sympy
def test_range_interval_intersection():
    p = symbols('p', positive=True)
    assert isinstance(Range(3).intersect(Interval(p, p + 2)), Intersection)
    assert Range(4).intersect(Interval(0, 3)) == Range(4)
    assert Range(4).intersect(Interval(-oo, oo)) == Range(4)
    assert Range(4).intersect(Interval(1, oo)) == Range(1, 4)
    assert Range(4).intersect(Interval(1.1, oo)) == Range(2, 4)
    assert Range(4).intersect(Interval(0.1, 3)) == Range(1, 4)
    assert Range(4).intersect(Interval(0.1, 3.1)) == Range(1, 4)
    assert Range(4).intersect(Interval.open(0, 3)) == Range(1, 3)
    assert Range(4).intersect(Interval.open(0.1, 0.5)) is S.EmptySet
コード例 #2
0
ファイル: test_util.py プロジェクト: baoqchau/sympy
def test_continuous_domain():
    x = Symbol('x')
    assert continuous_domain(sin(x), x, Interval(0, 2*pi)) == Interval(0, 2*pi)
    assert continuous_domain(tan(x), x, Interval(0, 2*pi)) == \
        Union(Interval(0, pi/2, False, True), Interval(pi/2, 3*pi/2, True, True),
              Interval(3*pi/2, 2*pi, True, False))
    assert continuous_domain((x - 1)/((x - 1)**2), x, S.Reals) == \
        Union(Interval(-oo, 1, True, True), Interval(1, oo, True, True))
    assert continuous_domain(log(x) + log(4*x - 1), x, S.Reals) == \
        Interval(1/4, oo, True, True)
    assert continuous_domain(1/sqrt(x - 3), x, S.Reals) == Interval(3, oo, True, True)
    assert continuous_domain(1/x - 2, x, S.Reals) == \
        Union(Interval.open(-oo, 0), Interval.open(0, oo))
    assert continuous_domain(1/(x**2 - 4) + 2, x, S.Reals) == \
        Union(Interval.open(-oo, -2), Interval.open(-2, 2), Interval.open(2, oo))
コード例 #3
0
ファイル: test_boolalg.py プロジェクト: asmeurer/sympy
def test_bool_as_set():
    assert ITE(y <= 0, False, y >= 1).as_set() == Interval(1, oo)
    assert And(x <= 2, x >= -2).as_set() == Interval(-2, 2)
    assert Or(x >= 2, x <= -2).as_set() == Interval(-oo, -2) + Interval(2, oo)
    assert Not(x > 2).as_set() == Interval(-oo, 2)
    # issue 10240
    assert Not(And(x > 2, x < 3)).as_set() == \
        Union(Interval(-oo, 2), Interval(3, oo))
    assert true.as_set() == S.UniversalSet
    assert false.as_set() == EmptySet()
    assert x.as_set() == S.UniversalSet
    assert And(Or(x < 1, x > 3), x < 2).as_set() == Interval.open(-oo, 1)
    assert And(x < 1, sin(x) < 3).as_set() == (x < 1).as_set()
    raises(NotImplementedError, lambda: (sin(x) < 1).as_set())
コード例 #4
0
    def _intersect(self, other):
        from sympy.functions.elementary.integers import ceiling, floor
        from sympy.functions.elementary.complexes import sign

        if other is S.Naturals:
            return self._intersect(Interval(1, S.Infinity))

        if other is S.Integers:
            return self

        if other.is_Interval:
            if not all(i.is_number for i in other.args[:2]):
                return

            # In case of null Range, return an EmptySet.
            if self.size == 0:
                return S.EmptySet

            # trim down to self's size, and represent
            # as a Range with step 1.
            start = ceiling(max(other.inf, self.inf))
            if start not in other:
                start += 1
            end = floor(min(other.sup, self.sup))
            if end not in other:
                end -= 1
            return self.intersect(Range(start, end + 1))

        if isinstance(other, Range):
            from sympy.solvers.diophantine import diop_linear
            from sympy.core.numbers import ilcm

            # non-overlap quick exits
            if not other:
                return S.EmptySet
            if not self:
                return S.EmptySet
            if other.sup < self.inf:
                return S.EmptySet
            if other.inf > self.sup:
                return S.EmptySet

            # work with finite end at the start
            r1 = self
            if r1.start.is_infinite:
                r1 = r1.reversed
            r2 = other
            if r2.start.is_infinite:
                r2 = r2.reversed

            # this equation represents the values of the Range;
            # it's a linear equation
            eq = lambda r, i: r.start + i * r.step

            # we want to know when the two equations might
            # have integer solutions so we use the diophantine
            # solver
            a, b = diop_linear(eq(r1, Dummy()) - eq(r2, Dummy()))

            # check for no solution
            no_solution = a is None and b is None
            if no_solution:
                return S.EmptySet

            # there is a solution
            # -------------------

            # find the coincident point, c
            a0 = a.as_coeff_Add()[0]
            c = eq(r1, a0)

            # find the first point, if possible, in each range
            # since c may not be that point
            def _first_finite_point(r1, c):
                if c == r1.start:
                    return c
                # st is the signed step we need to take to
                # get from c to r1.start
                st = sign(r1.start - c) * step
                # use Range to calculate the first point:
                # we want to get as close as possible to
                # r1.start; the Range will not be null since
                # it will at least contain c
                s1 = Range(c, r1.start + st, st)[-1]
                if s1 == r1.start:
                    pass
                else:
                    # if we didn't hit r1.start then, if the
                    # sign of st didn't match the sign of r1.step
                    # we are off by one and s1 is not in r1
                    if sign(r1.step) != sign(st):
                        s1 -= st
                if s1 not in r1:
                    return
                return s1

            # calculate the step size of the new Range
            step = abs(ilcm(r1.step, r2.step))
            s1 = _first_finite_point(r1, c)
            if s1 is None:
                return S.EmptySet
            s2 = _first_finite_point(r2, c)
            if s2 is None:
                return S.EmptySet

            # replace the corresponding start or stop in
            # the original Ranges with these points; the
            # result must have at least one point since
            # we know that s1 and s2 are in the Ranges
            def _updated_range(r, first):
                st = sign(r.step) * step
                if r.start.is_finite:
                    rv = Range(first, r.stop, st)
                else:
                    rv = Range(r.start, first + st, st)
                return rv

            r1 = _updated_range(self, s1)
            r2 = _updated_range(other, s2)

            # work with them both in the increasing direction
            if sign(r1.step) < 0:
                r1 = r1.reversed
            if sign(r2.step) < 0:
                r2 = r2.reversed

            # return clipped Range with positive step; it
            # can't be empty at this point
            start = max(r1.start, r2.start)
            stop = min(r1.stop, r2.stop)
            return Range(start, stop, step)
        else:
            return
コード例 #5
0
 def __eq__(self, other):
     return other == Interval(-S.Infinity, S.Infinity)
コード例 #6
0
    def _intersect(self, other):
        from sympy.solvers.diophantine import diophantine
        if self.base_set is S.Integers:
            g = None
            if isinstance(other, ImageSet) and other.base_set is S.Integers:
                g = other.lamda.expr
                m = other.lamda.variables[0]
            elif other is S.Integers:
                m = g = Dummy('x')
            if g is not None:
                f = self.lamda.expr
                n = self.lamda.variables[0]
                # Diophantine sorts the solutions according to the alphabetic
                # order of the variable names, since the result should not depend
                # on the variable name, they are replaced by the dummy variables
                # below
                a, b = Dummy('a'), Dummy('b')
                f, g = f.subs(n, a), g.subs(m, b)
                solns_set = diophantine(f - g)
                if solns_set == set():
                    return EmptySet()
                solns = list(diophantine(f - g))

                if len(solns) != 1:
                    return

                # since 'a' < 'b', select soln for n
                nsol = solns[0][0]
                t = nsol.free_symbols.pop()
                return imageset(Lambda(n, f.subs(a, nsol.subs(t, n))),
                                S.Integers)

        if other == S.Reals:
            from sympy.solvers.solveset import solveset_real
            from sympy.core.function import expand_complex
            if len(self.lamda.variables) > 1:
                return None

            f = self.lamda.expr
            n = self.lamda.variables[0]

            n_ = Dummy(n.name, real=True)
            f_ = f.subs(n, n_)

            re, im = f_.as_real_imag()
            im = expand_complex(im)

            return imageset(Lambda(n_, re),
                            self.base_set.intersect(solveset_real(im, n_)))

        elif isinstance(other, Interval):
            from sympy.solvers.solveset import (invert_real, invert_complex,
                                                solveset)

            f = self.lamda.expr
            n = self.lamda.variables[0]
            base_set = self.base_set
            new_inf, new_sup = None, None
            new_lopen, new_ropen = other.left_open, other.right_open

            if f.is_real:
                inverter = invert_real
            else:
                inverter = invert_complex

            g1, h1 = inverter(f, other.inf, n)
            g2, h2 = inverter(f, other.sup, n)

            if all(isinstance(i, FiniteSet) for i in (h1, h2)):
                if g1 == n:
                    if len(h1) == 1:
                        new_inf = h1.args[0]
                if g2 == n:
                    if len(h2) == 1:
                        new_sup = h2.args[0]
                # TODO: Design a technique to handle multiple-inverse
                # functions

                # Any of the new boundary values cannot be determined
                if any(i is None for i in (new_sup, new_inf)):
                    return

                range_set = S.EmptySet

                if all(i.is_real for i in (new_sup, new_inf)):
                    # this assumes continuity of underlying function
                    # however fixes the case when it is decreasing
                    if new_inf > new_sup:
                        new_inf, new_sup = new_sup, new_inf
                    new_interval = Interval(new_inf, new_sup, new_lopen,
                                            new_ropen)
                    range_set = base_set._intersect(new_interval)
                else:
                    if other.is_subset(S.Reals):
                        solutions = solveset(f, n, S.Reals)
                        if not isinstance(range_set, (ImageSet, ConditionSet)):
                            range_set = solutions._intersect(other)
                        else:
                            return

                if range_set is S.EmptySet:
                    return S.EmptySet
                elif isinstance(range_set,
                                Range) and range_set.size is not S.Infinity:
                    range_set = FiniteSet(*list(range_set))

                if range_set is not None:
                    return imageset(Lambda(n, f), range_set)
                return
            else:
                return
コード例 #7
0
ファイル: test_boolalg.py プロジェクト: sylee957/sympy
def test_multivariate_bool_as_set():
    x, y = symbols('x,y')

    assert And(x >= 0, y >= 0).as_set() == Interval(0, oo)*Interval(0, oo)
    assert Or(x >= 0, y >= 0).as_set() == S.Reals*S.Reals - \
        Interval(-oo, 0, True, True)*Interval(-oo, 0, True, True)
コード例 #8
0
ファイル: test_boolalg.py プロジェクト: sylee957/sympy
def test_issue_8975():
    assert Or(And(-oo < x, x <= -2), And(2 <= x, x < oo)).as_set() == \
        Interval(-oo, -2) + Interval(2, oo)
コード例 #9
0
ファイル: joint_rv_types.py プロジェクト: JSS95/sympy
 def set(self):
     return S.Reals * Interval(0, S.Infinity)
コード例 #10
0
ファイル: test_util.py プロジェクト: msgoff/sympy
def test_continuous_domain():
    x = Symbol("x")
    assert continuous_domain(sin(x), x,
                             Interval(0, 2 * pi)) == Interval(0, 2 * pi)
    assert continuous_domain(tan(x), x, Interval(0, 2 * pi)) == Union(
        Interval(0, pi / 2, False, True),
        Interval(pi / 2, pi * Rational(3, 2), True, True),
        Interval(pi * Rational(3, 2), 2 * pi, True, False),
    )
    assert continuous_domain((x - 1) / ((x - 1)**2), x,
                             S.Reals) == Union(Interval(-oo, 1, True, True),
                                               Interval(1, oo, True, True))
    assert continuous_domain(log(x) + log(4 * x - 1), x,
                             S.Reals) == Interval(Rational(1, 4), oo, True,
                                                  True)
    assert continuous_domain(1 / sqrt(x - 3), x,
                             S.Reals) == Interval(3, oo, True, True)
    assert continuous_domain(1 / x - 2, x,
                             S.Reals) == Union(Interval.open(-oo, 0),
                                               Interval.open(0, oo))
    assert continuous_domain(1 / (x**2 - 4) + 2, x,
                             S.Reals) == Union(Interval.open(-oo, -2),
                                               Interval.open(-2, 2),
                                               Interval.open(2, oo))
コード例 #11
0
ファイル: util.py プロジェクト: jamesBaker361/pynary
def function_range(f, symbol, domain):
    """
    Finds the range of a function in a given domain.
    This method is limited by the ability to determine the singularities and
    determine limits.

    Examples
    ========

    >>> from sympy import Symbol, S, exp, log, pi, sqrt, sin, tan
    >>> from sympy.sets import Interval
    >>> from sympy.calculus.util import function_range
    >>> x = Symbol('x')
    >>> function_range(sin(x), x, Interval(0, 2*pi))
    [-1, 1]
    >>> function_range(tan(x), x, Interval(-pi/2, pi/2))
    (-oo, oo)
    >>> function_range(1/x, x, S.Reals)
    (-oo, oo)
    >>> function_range(exp(x), x, S.Reals)
    (0, oo)
    >>> function_range(log(x), x, S.Reals)
    (-oo, oo)
    >>> function_range(sqrt(x), x , Interval(-5, 9))
    [0, 3]

    """
    from sympy.solvers.solveset import solveset

    vals = S.EmptySet
    period = periodicity(f, symbol)
    if not any(period is i for i in (None, S.Zero)):
        inf = domain.inf
        inf_period = S.Zero if inf.is_infinite else inf
        sup_period = inf_period + period
        periodic_interval = Interval(inf_period, sup_period)
        domain = domain.intersect(periodic_interval)

    intervals = continuous_domain(f, symbol, domain)
    range_int = S.EmptySet
    if isinstance(intervals, Interval):
        interval_iter = (intervals,)

    else:
        interval_iter = intervals.args

    for interval in interval_iter:
        critical_points = S.EmptySet
        critical_values = S.EmptySet
        bounds = ((interval.left_open, interval.inf, '+'),
                  (interval.right_open, interval.sup, '-'))

        for is_open, limit_point, direction in bounds:
            if is_open:
                critical_values += FiniteSet(limit(f, symbol, limit_point, direction))
                vals += critical_values

            else:
                vals += FiniteSet(f.subs(symbol, limit_point))

        critical_points += solveset(f.diff(symbol), symbol, domain)

        for critical_point in critical_points:
            vals += FiniteSet(f.subs(symbol, critical_point))

        left_open, right_open = False, False

        if critical_values is not S.EmptySet:
            if critical_values.inf == vals.inf:
                left_open = True

            if critical_values.sup == vals.sup:
                right_open = True

        range_int += Interval(vals.inf, vals.sup, left_open, right_open)

    return range_int
コード例 #12
0
def function_range(f, symbol, domain):
    """
    Finds the range of a function in a given domain.
    This method is limited by the ability to determine the singularities and
    determine limits.

    Examples
    ========

    >>> from sympy import Symbol, S, exp, log, pi, sqrt, sin, tan
    >>> from sympy.sets import Interval
    >>> from sympy.calculus.util import function_range
    >>> x = Symbol('x')
    >>> function_range(sin(x), x, Interval(0, 2*pi))
    Interval(-1, 1)
    >>> function_range(tan(x), x, Interval(-pi/2, pi/2))
    Interval(-oo, oo)
    >>> function_range(1/x, x, S.Reals)
    Union(Interval.open(-oo, 0), Interval.open(0, oo))
    >>> function_range(exp(x), x, S.Reals)
    Interval.open(0, oo)
    >>> function_range(log(x), x, S.Reals)
    Interval(-oo, oo)
    >>> function_range(sqrt(x), x , Interval(-5, 9))
    Interval(0, 3)

    """
    from sympy.solvers.solveset import solveset

    if isinstance(domain, EmptySet):
        return S.EmptySet

    period = periodicity(f, symbol)
    if period is S.Zero:
        # the expression is constant wrt symbol
        return FiniteSet(f.expand())

    if period is not None:
        if isinstance(domain, Interval):
            if (domain.inf - domain.sup).is_infinite:
                domain = Interval(0, period)
        elif isinstance(domain, Union):
            for sub_dom in domain.args:
                if isinstance(sub_dom, Interval) and \
                ((sub_dom.inf - sub_dom.sup).is_infinite):
                    domain = Interval(0, period)

    intervals = continuous_domain(f, symbol, domain)
    range_int = S.EmptySet
    if isinstance(intervals,(Interval, FiniteSet)):
        interval_iter = (intervals,)

    elif isinstance(intervals, Union):
        interval_iter = intervals.args

    else:
            raise NotImplementedError(filldedent('''
                Unable to find range for the given domain.
                '''))

    for interval in interval_iter:
        if isinstance(interval, FiniteSet):
            for singleton in interval:
                if singleton in domain:
                    range_int += FiniteSet(f.subs(symbol, singleton))
        elif isinstance(interval, Interval):
            vals = S.EmptySet
            critical_points = S.EmptySet
            critical_values = S.EmptySet
            bounds = ((interval.left_open, interval.inf, '+'),
                   (interval.right_open, interval.sup, '-'))

            for is_open, limit_point, direction in bounds:
                if is_open:
                    critical_values += FiniteSet(limit(f, symbol, limit_point, direction))
                    vals += critical_values

                else:
                    vals += FiniteSet(f.subs(symbol, limit_point))

            solution = solveset(f.diff(symbol), symbol, interval)

            if isinstance(solution, ConditionSet):
                raise NotImplementedError('Unable to find critical points for %s'.format(f))

            critical_points += solution

            for critical_point in critical_points:
                vals += FiniteSet(f.subs(symbol, critical_point))

            left_open, right_open = False, False

            if critical_values is not S.EmptySet:
                if critical_values.inf == vals.inf:
                    left_open = True

                if critical_values.sup == vals.sup:
                    right_open = True

            range_int += Interval(vals.inf, vals.sup, left_open, right_open)
        else:
            raise NotImplementedError(filldedent('''
                Unable to find range for the given domain.
                '''))

    return range_int
コード例 #13
0
ファイル: sequences.py プロジェクト: zh597588308/sympy
 def interval(self):
     return Interval(self.args[1][1], self.args[1][2])
コード例 #14
0
ファイル: Qu2v.py プロジェクト: cosmosZhou/sagemath
def prove(Eq):
    n = Symbol.n(integer=True, positive=True)
    u = Symbol.u(domain=Interval(0, n, integer=True))
    v = Symbol.v(domain=Interval(0, n, integer=True))
    Eq << apply(n, u, v)

    w, i, j = Eq[0].lhs.args
    Q = Eq[2].lhs.base

    Eq.x_slice_last, Eq.x_slice_domain = sets.imply.conditionset.apply(
        Q[u]).split()

    Eq << Eq.x_slice_domain.apply(
        discrete.combinatorics.permutation.index.equality, v)
    Eq.h_domain, Eq.x_h_equality = Eq[-1].split()

    hv = Eq.x_h_equality.function.lhs.indices[0]
    Eq << algebre.matrix.elementary.swap.invariant.permutation.apply(n + 1,
                                                                     w=w)

    Eq << Subset(Eq[-2].limits[0][1], Eq[-1].rhs, plausible=True)

    Eq << sets.subset.forall.imply.forall.apply(Eq[-1], Eq[-2])

    Eq << Eq[-1].subs(Eq[-1].rhs.this.definition)

    Eq << Eq[-1].subs(i, n)

    Eq << Eq[-1].subs(j, hv)

    k = Eq[-1].function.lhs.function.arg.args[0].indices[-1]
    Eq.Xv_definition = Eq[1].subs(j, v)

    Eq << Eq.Xv_definition[k].set.union_comprehension((k, 0, n))

    Eq.x_n1_set_comprehension = Eq[-2].subs(Eq[-1].reversed)

    Eq << Eq.Xv_definition[n]

    Eq << Eq[0].subs(i, n).subs(j, hv)[n]

    Eq << Eq[-2].this.rhs.subs(Eq[-1])

    Eq << Eq[-1].this.rhs.expand()

    Eq << Eq[-1].subs(Eq.x_h_equality)

    Eq << Eq[-1].this.function.as_Or()

    Eq << (Eq[-1] & Eq.h_domain).split()

    Eq <<= Eq.x_n1_set_comprehension & Eq[-1]

    Eq.Xv_in_Qv, Eq.x_eq_swap_Xv = Eq[3].split()

    Eq << Eq.Xv_in_Qv.definition

    Eq.indexu_eq_indexu = Eq.x_eq_swap_Xv.function.rhs.args[0].indices[
        1].this.subs(Eq.Xv_definition)

    Eq.indexu_eq_indexv = Eq.x_slice_domain.apply(
        discrete.combinatorics.permutation.index.swap, u, v, w=w)

    Eq.indexu_contains, Eq.x_indexu_equality = Eq.x_slice_domain.apply(
        discrete.combinatorics.permutation.index.equality, u).split()

    Eq.equality_of_indexu_and_n = Eq.x_indexu_equality + Eq.x_slice_last.reversed

    i = Symbol.i(domain=Interval(0, n, integer=True))
    j = Symbol.j(domain=Interval(0, n, integer=True))

    Eq << Eq.x_slice_domain.apply(
        discrete.combinatorics.permutation.index.kronecker_delta.indexOf, i, j)

    x = Eq[-1].variable.base
    Eq << Eq[-1].subs(i, x[n]).split()

    Eq << Eq[-2].subs(Eq.x_slice_last)

    m = Symbol.m(domain=Interval(0, n, integer=True))
    Eq.indexOf_indexed = Eq.x_slice_domain.apply(
        discrete.combinatorics.permutation.index.indexOf_indexed, j=m)

    Eq << Eq.indexOf_indexed.subs(m, n)
    Eq << Eq[-2].subs(Eq[-1])

    Eq << Eq[-1].subs(j, Eq.equality_of_indexu_and_n.function.lhs).split()

    Eq << Eq[-2].subs(Eq.x_indexu_equality)

    Eq << Eq.indexOf_indexed.subs(
        m, Eq.equality_of_indexu_and_n.function.lhs.indices[0]).split()

    Eq <<= Eq.indexu_contains & Eq[-2]
    Eq << Eq[-3].subs(Eq[-1])

    Eq << Eq[-1].subs(Eq.equality_of_indexu_and_n)

    Eq << Eq[-1].this.function.lhs.as_Piecewise()

    Eq << Eq[-1].this.function.as_Or()

    Eq << Eq.indexu_eq_indexv.subs(Eq[-1].reversed)

    Eq << Eq.indexu_eq_indexu.subs(Eq[-1])

    Eq << Eq.x_eq_swap_Xv.subs(Eq[-1])

    Eq << Eq[-1].subs(Eq.Xv_definition)

    Eq << algebre.matrix.elementary.swap.multiply.left.apply(
        x[:n + 1], i=n, j=Eq.h_domain.lhs, w=w)

    Eq << Eq[-2].subs(Eq[-1])
コード例 #15
0
def test_not_empty_in():
    assert not_empty_in(FiniteSet(x, 2*x).intersect(Interval(1, 2, True, False)), x) == \
        Interval(S(1)/2, 2, True, False)
    assert not_empty_in(FiniteSet(x, x**2).intersect(Interval(1, 2)), x) == \
        Union(Interval(-sqrt(2), -1), Interval(1, 2))
    assert not_empty_in(FiniteSet(x**2 + x, x).intersect(Interval(2, 4)), x) == \
        Union(Interval(-sqrt(17)/2 - S(1)/2, -2),
              Interval(1, -S(1)/2 + sqrt(17)/2), Interval(2, 4))
    assert not_empty_in(FiniteSet(x/(x - 1)).intersect(S.Reals), x) == \
        Complement(S.Reals, FiniteSet(1))
    assert not_empty_in(FiniteSet(a/(a - 1)).intersect(S.Reals), a) == \
        Complement(S.Reals, FiniteSet(1))
    assert not_empty_in(FiniteSet((x**2 - 3*x + 2)/(x - 1)).intersect(S.Reals), x) == \
        Complement(S.Reals, FiniteSet(1))
    assert not_empty_in(FiniteSet(3, 4, x/(x - 1)).intersect(Interval(2, 3)), x) == \
        Union(Interval(S(3)/2, 2), FiniteSet(3))
    assert not_empty_in(FiniteSet(x/(x**2 - 1)).intersect(S.Reals), x) == \
        Complement(S.Reals, FiniteSet(-1, 1))
    assert not_empty_in(FiniteSet(x, x**2).intersect(Union(Interval(1, 3, True, True),
                                                           Interval(4, 5))), x) == \
        Union(Interval(-sqrt(5), -2), Interval(-sqrt(3), -1, True, True),
              Interval(1, 3, True, True), Interval(4, 5))
    assert not_empty_in(FiniteSet(1).intersect(Interval(3, 4)),
                        x) == S.EmptySet
    assert not_empty_in(FiniteSet(x**2/(x + 2)).intersect(Interval(1, oo)), x) == \
        Union(Interval(-2, -1, True, False), Interval(2, oo))
コード例 #16
0
ファイル: test_fancysets.py プロジェクト: dagidagi1/Matrix
def test_union_RealSubSet():
    assert (S.Complexes).union(Interval(1, 2)) == S.Complexes
    assert (S.Complexes).union(S.Integers) == S.Complexes
コード例 #17
0
ファイル: joint_rv_types.py プロジェクト: JSS95/sympy
 def set(self):
     k = len(self.alpha)
     return Interval(0, 1)**k
コード例 #18
0
ファイル: test_util.py プロジェクト: msgoff/sympy
def test_issue_16469():
    x = Symbol("x", real=True)
    f = abs(x)
    assert function_range(f, x, S.Reals) == Interval(0, oo, False, True)
コード例 #19
0
ファイル: joint_rv_types.py プロジェクト: JSS95/sympy
 def set(self):
     return Intersection(S.Naturals0, Interval(0, self.n))**len(self.p)
コード例 #20
0
ファイル: test_relational.py プロジェクト: yang603/sympy
def test_multivariate_relational_as_set():
    assert (x*y >= 0).as_set() == Interval(0, oo)*Interval(0, oo) + \
        Interval(-oo, 0)*Interval(-oo, 0)
コード例 #21
0
ファイル: test_pickling.py プロジェクト: msgoff/sympy
def test_core_interval():
    for c in (Interval, Interval(0, 2)):
        check(c)
コード例 #22
0
ファイル: test_boolalg.py プロジェクト: sylee957/sympy
def test_issue_8777():
    assert And(x > 2, x < oo).as_set() == Interval(2, oo, left_open=True)
    assert And(x >= 1, x < oo).as_set() == Interval(1, oo)
    assert (x < oo).as_set() == Interval(-oo, oo)
    assert (x > -oo).as_set() == Interval(-oo, oo)
コード例 #23
0
def function_range(f, symbol, domain):
    """
    Finds the range of a function in a given domain.
    This method is limited by the ability to determine the singularities and
    determine limits.

    Parameters
    ==========

    f : :py:class:`~.Expr`
        The concerned function.
    symbol : :py:class:`~.Symbol`
        The variable for which the range of function is to be determined.
    domain : :py:class:`~.Interval`
        The domain under which the range of the function has to be found.

    Examples
    ========

    >>> from sympy import Interval, Symbol, S, exp, log, pi, sqrt, sin, tan
    >>> from sympy.calculus.util import function_range
    >>> x = Symbol('x')
    >>> function_range(sin(x), x, Interval(0, 2*pi))
    Interval(-1, 1)
    >>> function_range(tan(x), x, Interval(-pi/2, pi/2))
    Interval(-oo, oo)
    >>> function_range(1/x, x, S.Reals)
    Union(Interval.open(-oo, 0), Interval.open(0, oo))
    >>> function_range(exp(x), x, S.Reals)
    Interval.open(0, oo)
    >>> function_range(log(x), x, S.Reals)
    Interval(-oo, oo)
    >>> function_range(sqrt(x), x, Interval(-5, 9))
    Interval(0, 3)

    Returns
    =======

    :py:class:`~.Interval`
        Union of all ranges for all intervals under domain where function is
        continuous.

    Raises
    ======

    NotImplementedError
        If any of the intervals, in the given domain, for which function
        is continuous are not finite or real,
        OR if the critical points of the function on the domain cannot be found.
    """

    if domain is S.EmptySet:
        return S.EmptySet

    period = periodicity(f, symbol)
    if period == S.Zero:
        # the expression is constant wrt symbol
        return FiniteSet(f.expand())

    from sympy.series.limits import limit
    from sympy.solvers.solveset import solveset

    if period is not None:
        if isinstance(domain, Interval):
            if (domain.inf - domain.sup).is_infinite:
                domain = Interval(0, period)
        elif isinstance(domain, Union):
            for sub_dom in domain.args:
                if isinstance(sub_dom, Interval) and \
                ((sub_dom.inf - sub_dom.sup).is_infinite):
                    domain = Interval(0, period)

    intervals = continuous_domain(f, symbol, domain)
    range_int = S.EmptySet
    if isinstance(intervals, (Interval, FiniteSet)):
        interval_iter = (intervals, )

    elif isinstance(intervals, Union):
        interval_iter = intervals.args

    else:
        raise NotImplementedError(
            filldedent('''
                Unable to find range for the given domain.
                '''))

    for interval in interval_iter:
        if isinstance(interval, FiniteSet):
            for singleton in interval:
                if singleton in domain:
                    range_int += FiniteSet(f.subs(symbol, singleton))
        elif isinstance(interval, Interval):
            vals = S.EmptySet
            critical_points = S.EmptySet
            critical_values = S.EmptySet
            bounds = ((interval.left_open, interval.inf, '+'),
                      (interval.right_open, interval.sup, '-'))

            for is_open, limit_point, direction in bounds:
                if is_open:
                    critical_values += FiniteSet(
                        limit(f, symbol, limit_point, direction))
                    vals += critical_values

                else:
                    vals += FiniteSet(f.subs(symbol, limit_point))

            solution = solveset(f.diff(symbol), symbol, interval)

            if not iterable(solution):
                raise NotImplementedError(
                    'Unable to find critical points for {}'.format(f))
            if isinstance(solution, ImageSet):
                raise NotImplementedError(
                    'Infinite number of critical points for {}'.format(f))

            critical_points += solution

            for critical_point in critical_points:
                vals += FiniteSet(f.subs(symbol, critical_point))

            left_open, right_open = False, False

            if critical_values is not S.EmptySet:
                if critical_values.inf == vals.inf:
                    left_open = True

                if critical_values.sup == vals.sup:
                    right_open = True

            range_int += Interval(vals.inf, vals.sup, left_open, right_open)
        else:
            raise NotImplementedError(
                filldedent('''
                Unable to find range for the given domain.
                '''))

    return range_int
コード例 #24
0
 def __new__(cls):
     return Interval.__new__(cls, -S.Infinity, S.Infinity)
コード例 #25
0
def bspline_basis(d, knots, n, x):
    """
    The $n$-th B-spline at $x$ of degree $d$ with knots.

    Explanation
    ===========

    B-Splines are piecewise polynomials of degree $d$. They are defined on a
    set of knots, which is a sequence of integers or floats.

    Examples
    ========

    The 0th degree splines have a value of 1 on a single interval:

        >>> from sympy import bspline_basis
        >>> from sympy.abc import x
        >>> d = 0
        >>> knots = tuple(range(5))
        >>> bspline_basis(d, knots, 0, x)
        Piecewise((1, (x >= 0) & (x <= 1)), (0, True))

    For a given ``(d, knots)`` there are ``len(knots)-d-1`` B-splines
    defined, that are indexed by ``n`` (starting at 0).

    Here is an example of a cubic B-spline:

        >>> bspline_basis(3, tuple(range(5)), 0, x)
        Piecewise((x**3/6, (x >= 0) & (x <= 1)),
                  (-x**3/2 + 2*x**2 - 2*x + 2/3,
                  (x >= 1) & (x <= 2)),
                  (x**3/2 - 4*x**2 + 10*x - 22/3,
                  (x >= 2) & (x <= 3)),
                  (-x**3/6 + 2*x**2 - 8*x + 32/3,
                  (x >= 3) & (x <= 4)),
                  (0, True))

    By repeating knot points, you can introduce discontinuities in the
    B-splines and their derivatives:

        >>> d = 1
        >>> knots = (0, 0, 2, 3, 4)
        >>> bspline_basis(d, knots, 0, x)
        Piecewise((1 - x/2, (x >= 0) & (x <= 2)), (0, True))

    It is quite time consuming to construct and evaluate B-splines. If
    you need to evaluate a B-spline many times, it is best to lambdify them
    first:

        >>> from sympy import lambdify
        >>> d = 3
        >>> knots = tuple(range(10))
        >>> b0 = bspline_basis(d, knots, 0, x)
        >>> f = lambdify(x, b0)
        >>> y = f(0.5)

    Parameters
    ==========

    d : integer
        degree of bspline

    knots : list of integer values
        list of knots points of bspline

    n : integer
        $n$-th B-spline

    x : symbol

    See Also
    ========

    bspline_basis_set

    References
    ==========

    .. [1] https://en.wikipedia.org/wiki/B-spline

    """
    # make sure x has no assumptions so conditions don't evaluate
    xvar = x
    x = Dummy()

    knots = tuple(sympify(k) for k in knots)
    d = int(d)
    n = int(n)
    n_knots = len(knots)
    n_intervals = n_knots - 1
    if n + d + 1 > n_intervals:
        raise ValueError("n + d + 1 must not exceed len(knots) - 1")
    if d == 0:
        result = Piecewise(
            (S.One, Interval(knots[n], knots[n + 1]).contains(x)), (0, True)
        )
    elif d > 0:
        denom = knots[n + d + 1] - knots[n + 1]
        if denom != S.Zero:
            B = (knots[n + d + 1] - x) / denom
            b2 = bspline_basis(d - 1, knots, n + 1, x)
        else:
            b2 = B = S.Zero

        denom = knots[n + d] - knots[n]
        if denom != S.Zero:
            A = (x - knots[n]) / denom
            b1 = bspline_basis(d - 1, knots, n, x)
        else:
            b1 = A = S.Zero

        result = _add_splines(A, b1, B, b2, x)
    else:
        raise ValueError("degree must be non-negative: %r" % n)

    # return result with user-given x
    return result.xreplace({x: xvar})
コード例 #26
0
 def __hash__(self):
     return hash(Interval(-S.Infinity, S.Infinity))
コード例 #27
0
ファイル: test_util.py プロジェクト: msgoff/sympy
def test_not_empty_in():
    assert not_empty_in(
        FiniteSet(x, 2 * x).intersect(Interval(1, 2, True, False)),
        x) == Interval(S.Half, 2, True, False)
    assert not_empty_in(FiniteSet(x, x**2).intersect(Interval(1, 2)),
                        x) == Union(Interval(-sqrt(2), -1), Interval(1, 2))
    assert not_empty_in(FiniteSet(x**2 + x, x).intersect(Interval(2, 4)),
                        x) == Union(
                            Interval(-sqrt(17) / 2 - S.Half, -2),
                            Interval(1,
                                     Rational(-1, 2) + sqrt(17) / 2),
                            Interval(2, 4),
                        )
    assert not_empty_in(FiniteSet(x / (x - 1)).intersect(S.Reals),
                        x) == Complement(S.Reals, FiniteSet(1))
    assert not_empty_in(FiniteSet(a / (a - 1)).intersect(S.Reals),
                        a) == Complement(S.Reals, FiniteSet(1))
    assert not_empty_in(
        FiniteSet((x**2 - 3 * x + 2) / (x - 1)).intersect(S.Reals),
        x) == Complement(S.Reals, FiniteSet(1))
    assert not_empty_in(
        FiniteSet(3, 4, x / (x - 1)).intersect(Interval(2, 3)),
        x) == Interval(-oo, oo)
    assert not_empty_in(
        FiniteSet(4, x / (x - 1)).intersect(Interval(2, 3)),
        x) == Interval(S(3) / 2, 2)
    assert not_empty_in(FiniteSet(x / (x**2 - 1)).intersect(S.Reals),
                        x) == Complement(S.Reals, FiniteSet(-1, 1))
    assert not_empty_in(
        FiniteSet(x, x**2).intersect(
            Union(Interval(1, 3, True, True), Interval(4, 5))),
        x,
    ) == Union(
        Interval(-sqrt(5), -2),
        Interval(-sqrt(3), -1, True, True),
        Interval(1, 3, True, True),
        Interval(4, 5),
    )
    assert not_empty_in(FiniteSet(1).intersect(Interval(3, 4)),
                        x) == S.EmptySet
    assert not_empty_in(
        FiniteSet(x**2 / (x + 2)).intersect(Interval(1, oo)),
        x) == Union(Interval(-2, -1, True, False), Interval(2, oo))
    raises(ValueError, lambda: not_empty_in(x))
    raises(ValueError, lambda: not_empty_in(Interval(0, 1), x))
    raises(NotImplementedError,
           lambda: not_empty_in(FiniteSet(x).intersect(S.Reals), x, a))
コード例 #28
0
 def _intersect(self, other):
     if other.is_Interval:
         return Intersection(S.Integers, other,
                             Interval(self._inf, S.Infinity))
     return None
コード例 #29
0
def test_normalize_theta_set():

    # Interval
    assert normalize_theta_set(Interval(pi, 2*pi)) == \
        Union(FiniteSet(0), Interval.Ropen(pi, 2*pi))
    assert normalize_theta_set(Interval(9*pi/2, 5*pi)) == Interval(pi/2, pi)
    assert normalize_theta_set(Interval(-3*pi/2, pi/2)) == Interval.Ropen(0, 2*pi)
    assert normalize_theta_set(Interval.open(-3*pi/2, pi/2)) == \
        Union(Interval.Ropen(0, pi/2), Interval.open(pi/2, 2*pi))
    assert normalize_theta_set(Interval.open(-7*pi/2, -3*pi/2)) == \
        Union(Interval.Ropen(0, pi/2), Interval.open(pi/2, 2*pi))
    assert normalize_theta_set(Interval(-pi/2, pi/2)) == \
        Union(Interval(0, pi/2), Interval.Ropen(3*pi/2, 2*pi))
    assert normalize_theta_set(Interval.open(-pi/2, pi/2)) == \
        Union(Interval.Ropen(0, pi/2), Interval.open(3*pi/2, 2*pi))
    assert normalize_theta_set(Interval(-4*pi, 3*pi)) == Interval.Ropen(0, 2*pi)
    assert normalize_theta_set(Interval(-3*pi/2, -pi/2)) == Interval(pi/2, 3*pi/2)
    assert normalize_theta_set(Interval.open(0, 2*pi)) == Interval.open(0, 2*pi)
    assert normalize_theta_set(Interval.Ropen(-pi/2, pi/2)) == \
        Union(Interval.Ropen(0, pi/2), Interval.Ropen(3*pi/2, 2*pi))
    assert normalize_theta_set(Interval.Lopen(-pi/2, pi/2)) == \
        Union(Interval(0, pi/2), Interval.open(3*pi/2, 2*pi))
    assert normalize_theta_set(Interval(-pi/2, pi/2)) == \
        Union(Interval(0, pi/2), Interval.Ropen(3*pi/2, 2*pi))
    assert normalize_theta_set(Interval.open(4*pi, 9*pi/2)) == Interval.open(0, pi/2)
    assert normalize_theta_set(Interval.Lopen(4*pi, 9*pi/2)) == Interval.Lopen(0, pi/2)
    assert normalize_theta_set(Interval.Ropen(4*pi, 9*pi/2)) == Interval.Ropen(0, pi/2)
    assert normalize_theta_set(Interval.open(3*pi, 5*pi)) == \
        Union(Interval.Ropen(0, pi), Interval.open(pi, 2*pi))

    # FiniteSet
    assert normalize_theta_set(FiniteSet(0, pi, 3*pi)) == FiniteSet(0, pi)
    assert normalize_theta_set(FiniteSet(0, pi/2, pi, 2*pi)) == FiniteSet(0, pi/2, pi)
    assert normalize_theta_set(FiniteSet(0, -pi/2, -pi, -2*pi)) == FiniteSet(0, pi, 3*pi/2)
    assert normalize_theta_set(FiniteSet(-3*pi/2, pi/2)) == \
        FiniteSet(pi/2)
    assert normalize_theta_set(FiniteSet(2*pi)) == FiniteSet(0)

    # Unions
    assert normalize_theta_set(Union(Interval(0, pi/3), Interval(pi/2, pi))) == \
        Union(Interval(0, pi/3), Interval(pi/2, pi))
    assert normalize_theta_set(Union(Interval(0, pi), Interval(2*pi, 7*pi/3))) == \
        Interval(0, pi)

    # ValueError for non-real sets
    raises(ValueError, lambda: normalize_theta_set(S.Complexes))
コード例 #30
0
def normalize_theta_set(theta):
    """
    Normalize a Real Set `theta` in the Interval [0, 2*pi). It returns
    a normalized value of theta in the Set. For Interval, a maximum of
    one cycle [0, 2*pi], is returned i.e. for theta equal to [0, 10*pi],
    returned normalized value would be [0, 2*pi). As of now intervals
    with end points as non-multiples of `pi` is not supported.

    Raises
    ======

    NotImplementedError
        The algorithms for Normalizing theta Set are not yet
        implemented.
    ValueError
        The input is not valid, i.e. the input is not a real set.
    RuntimeError
        It is a bug, please report to the github issue tracker.

    Examples
    ========

    >>> from sympy.sets.fancysets import normalize_theta_set
    >>> from sympy import Interval, FiniteSet, pi
    >>> normalize_theta_set(Interval(9*pi/2, 5*pi))
    [pi/2, pi]
    >>> normalize_theta_set(Interval(-3*pi/2, pi/2))
    [0, 2*pi)
    >>> normalize_theta_set(Interval(-pi/2, pi/2))
    [0, pi/2] U [3*pi/2, 2*pi)
    >>> normalize_theta_set(Interval(-4*pi, 3*pi))
    [0, 2*pi)
    >>> normalize_theta_set(Interval(-3*pi/2, -pi/2))
    [pi/2, 3*pi/2]
    >>> normalize_theta_set(FiniteSet(0, pi, 3*pi))
    {0, pi}

    """
    from sympy.functions.elementary.trigonometric import _pi_coeff as coeff

    if theta.is_Interval:
        interval_len = theta.measure
        # one complete circle
        if interval_len >= 2 * S.Pi:
            if interval_len == 2 * S.Pi and theta.left_open and theta.right_open:
                k = coeff(theta.start)
                return Union(Interval(0, k * S.Pi, False, True),
                             Interval(k * S.Pi, 2 * S.Pi, True, True))
            return Interval(0, 2 * S.Pi, False, True)

        k_start, k_end = coeff(theta.start), coeff(theta.end)

        if k_start is None or k_end is None:
            raise NotImplementedError(
                "Normalizing theta without pi as coefficient is "
                "not yet implemented")
        new_start = k_start * S.Pi
        new_end = k_end * S.Pi

        if new_start > new_end:
            return Union(Interval(S.Zero, new_end, False, theta.right_open),
                         Interval(new_start, 2 * S.Pi, theta.left_open, True))
        else:
            return Interval(new_start, new_end, theta.left_open,
                            theta.right_open)

    elif theta.is_FiniteSet:
        new_theta = []
        for element in theta:
            k = coeff(element)
            if k is None:
                raise NotImplementedError('Normalizing theta without pi as '
                                          'coefficient, is not Implemented.')
            else:
                new_theta.append(k * S.Pi)
        return FiniteSet(*new_theta)

    elif theta.is_Union:
        return Union(
            *[normalize_theta_set(interval) for interval in theta.args])

    elif theta.is_subset(S.Reals):
        raise NotImplementedError(
            "Normalizing theta when, it is of type %s is not "
            "implemented" % type(theta))
    else:
        raise ValueError(" %s is not a real set" % (theta))
コード例 #31
0
ファイル: test_fancysets.py プロジェクト: dagidagi1/Matrix
def test_ComplexRegion_from_real():
    c1 = ComplexRegion(Interval(0, 1) * Interval(0, 2 * S.Pi), polar=True)

    raises(ValueError, lambda: c1.from_real(c1))
    assert c1.from_real(Interval(-1, 1)) == ComplexRegion(Interval(-1, 1) * FiniteSet(0), False)
コード例 #32
0
ファイル: test_util.py プロジェクト: msgoff/sympy
def test_is_convex():
    assert is_convex(1 / x, x, domain=Interval(0, oo)) == True
    assert is_convex(1 / x, x, domain=Interval(-oo, 0)) == False
    assert is_convex(x**2, x, domain=Interval(0, oo)) == True
    assert is_convex(log(x), x) == False
    raises(NotImplementedError, lambda: is_convex(log(x), x, a))
コード例 #33
0
ファイル: test_fancysets.py プロジェクト: dagidagi1/Matrix
def test_normalize_theta_set():
    # Interval
    assert normalize_theta_set(Interval(pi, 2*pi)) == \
        Union(FiniteSet(0), Interval.Ropen(pi, 2*pi))
    assert normalize_theta_set(Interval(pi*Rational(9, 2), 5*pi)) == Interval(pi/2, pi)
    assert normalize_theta_set(Interval(pi*Rational(-3, 2), pi/2)) == Interval.Ropen(0, 2*pi)
    assert normalize_theta_set(Interval.open(pi*Rational(-3, 2), pi/2)) == \
        Union(Interval.Ropen(0, pi/2), Interval.open(pi/2, 2*pi))
    assert normalize_theta_set(Interval.open(pi*Rational(-7, 2), pi*Rational(-3, 2))) == \
        Union(Interval.Ropen(0, pi/2), Interval.open(pi/2, 2*pi))
    assert normalize_theta_set(Interval(-pi/2, pi/2)) == \
        Union(Interval(0, pi/2), Interval.Ropen(pi*Rational(3, 2), 2*pi))
    assert normalize_theta_set(Interval.open(-pi/2, pi/2)) == \
        Union(Interval.Ropen(0, pi/2), Interval.open(pi*Rational(3, 2), 2*pi))
    assert normalize_theta_set(Interval(-4*pi, 3*pi)) == Interval.Ropen(0, 2*pi)
    assert normalize_theta_set(Interval(pi*Rational(-3, 2), -pi/2)) == Interval(pi/2, pi*Rational(3, 2))
    assert normalize_theta_set(Interval.open(0, 2*pi)) == Interval.open(0, 2*pi)
    assert normalize_theta_set(Interval.Ropen(-pi/2, pi/2)) == \
        Union(Interval.Ropen(0, pi/2), Interval.Ropen(pi*Rational(3, 2), 2*pi))
    assert normalize_theta_set(Interval.Lopen(-pi/2, pi/2)) == \
        Union(Interval(0, pi/2), Interval.open(pi*Rational(3, 2), 2*pi))
    assert normalize_theta_set(Interval(-pi/2, pi/2)) == \
        Union(Interval(0, pi/2), Interval.Ropen(pi*Rational(3, 2), 2*pi))
    assert normalize_theta_set(Interval.open(4*pi, pi*Rational(9, 2))) == Interval.open(0, pi/2)
    assert normalize_theta_set(Interval.Lopen(4*pi, pi*Rational(9, 2))) == Interval.Lopen(0, pi/2)
    assert normalize_theta_set(Interval.Ropen(4*pi, pi*Rational(9, 2))) == Interval.Ropen(0, pi/2)
    assert normalize_theta_set(Interval.open(3*pi, 5*pi)) == \
        Union(Interval.Ropen(0, pi), Interval.open(pi, 2*pi))

    # FiniteSet
    assert normalize_theta_set(FiniteSet(0, pi, 3*pi)) == FiniteSet(0, pi)
    assert normalize_theta_set(FiniteSet(0, pi/2, pi, 2*pi)) == FiniteSet(0, pi/2, pi)
    assert normalize_theta_set(FiniteSet(0, -pi/2, -pi, -2*pi)) == FiniteSet(0, pi, pi*Rational(3, 2))
    assert normalize_theta_set(FiniteSet(pi*Rational(-3, 2), pi/2)) == \
        FiniteSet(pi/2)
    assert normalize_theta_set(FiniteSet(2*pi)) == FiniteSet(0)

    # Unions
    assert normalize_theta_set(Union(Interval(0, pi/3), Interval(pi/2, pi))) == \
        Union(Interval(0, pi/3), Interval(pi/2, pi))
    assert normalize_theta_set(Union(Interval(0, pi), Interval(2*pi, pi*Rational(7, 3)))) == \
        Interval(0, pi)

    # ValueError for non-real sets
    raises(ValueError, lambda: normalize_theta_set(S.Complexes))

    # NotImplementedError for subset of reals
    raises(NotImplementedError, lambda: normalize_theta_set(Interval(0, 1)))

    # NotImplementedError without pi as coefficient
    raises(NotImplementedError, lambda: normalize_theta_set(Interval(1, 2*pi)))
    raises(NotImplementedError, lambda: normalize_theta_set(Interval(2*pi, 10)))
    raises(NotImplementedError, lambda: normalize_theta_set(FiniteSet(0, 3, 3*pi)))
コード例 #34
0
ファイル: fancysets.py プロジェクト: atsao72/sympy
 def __new__(cls):
     return Interval.__new__(cls, -S.Infinity, S.Infinity)
コード例 #35
0
ファイル: test_util.py プロジェクト: msgoff/sympy
def test_function_range():
    x, y, a, b = symbols("x y a b")
    assert function_range(sin(x), x, Interval(-pi / 2,
                                              pi / 2)) == Interval(-1, 1)
    assert function_range(sin(x), x, Interval(0, pi)) == Interval(0, 1)
    assert function_range(tan(x), x, Interval(0, pi)) == Interval(-oo, oo)
    assert function_range(tan(x), x, Interval(pi / 2, pi)) == Interval(-oo, 0)
    assert function_range((x + 3) / (x - 2), x,
                          Interval(-5,
                                   5)) == Union(Interval(-oo, Rational(2, 7)),
                                                Interval(Rational(8, 3), oo))
    assert function_range(1 / (x**2), x, Interval(-1, 1)) == Interval(1, oo)
    assert function_range(exp(x), x, Interval(-1,
                                              1)) == Interval(exp(-1), exp(1))
    assert function_range(log(x) - x, x, S.Reals) == Interval(-oo, -1)
    assert function_range(sqrt(3 * x - 1), x,
                          Interval(0, 2)) == Interval(0, sqrt(5))
    assert function_range(x * (x - 1) - (x**2 - x), x, S.Reals) == FiniteSet(0)
    assert function_range(x * (x - 1) - (x**2 - x) + y, x,
                          S.Reals) == FiniteSet(y)
    assert function_range(sin(x), x, Union(Interval(-5, -3),
                                           FiniteSet(4))) == Union(
                                               Interval(-sin(3), 1),
                                               FiniteSet(sin(4)))
    assert function_range(cos(x), x, Interval(-oo, -4)) == Interval(-1, 1)
    assert function_range(cos(x), x, S.EmptySet) == S.EmptySet
    raises(
        NotImplementedError,
        lambda: function_range(exp(x) * (sin(x) - cos(x)) / 2 - x, x, S.Reals),
    )
    raises(NotImplementedError,
           lambda: function_range(sin(x) + x, x, S.Reals))  # issue 13273
    raises(NotImplementedError, lambda: function_range(log(x), x, S.Integers))
    raises(NotImplementedError,
           lambda: function_range(sin(x) / 2, x, S.Naturals))