This file is indexed.

/usr/share/pyshared/sympy/series/limits.py is in python-sympy 0.7.1.rc1-3.

This file is owned by root:root, with mode 0o644.

The actual contents of the file can be viewed below.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
from sympy.core import S, Add, sympify, Expr, PoleError, Mul, oo, C
from gruntz import gruntz
from sympy.functions import sign, tan, cot

def limit(e, z, z0, dir="+"):
    """
    Compute the limit of e(z) at the point z0.

    z0 can be any expression, including oo and -oo.

    For dir="+" (default) it calculates the limit from the right
    (z->z0+) and for dir="-" the limit from the left (z->z0-). For infinite z0
    (oo or -oo), the dir argument doesn't matter.

    Examples:

    >>> from sympy import limit, sin, Symbol, oo
    >>> from sympy.abc import x
    >>> limit(sin(x)/x, x, 0)
    1
    >>> limit(1/x, x, 0, dir="+")
    oo
    >>> limit(1/x, x, 0, dir="-")
    -oo
    >>> limit(1/x, x, oo)
    0

    Strategy:

    First we try some heuristics for easy and frequent cases like "x", "1/x",
    "x**2" and similar, so that it's fast. For all other cases, we use the
    Gruntz algorithm (see the gruntz() function).
    """
    from sympy import Wild, log

    e = sympify(e)
    z = sympify(z)
    z0 = sympify(z0)

    if e == z:
        return z0

    if e.is_Rational:
        return e

    if not e.has(z):
        return e

    if e.func is tan:
        # discontinuity at odd multiples of pi/2; 0 at even
        disc = S.Pi/2
        sign = 1
        if dir == '-':
            sign *= -1
        i = limit(sign*e.args[0], z, z0)/disc
        if i.is_integer:
            if i.is_even:
                return S.Zero
            elif i.is_odd:
                if dir == '+':
                    return S.NegativeInfinity
                else:
                    return S.Infinity

    if e.func is cot:
        # discontinuity at multiples of pi; 0 at odd pi/2 multiples
        disc = S.Pi
        sign = 1
        if dir == '-':
            sign *= -1
        i = limit(sign*e.args[0], z, z0)/disc
        if i.is_integer:
            if dir == '-':
                return S.NegativeInfinity
            else:
                return S.Infinity
        elif (2*i).is_integer:
            return S.Zero

    if e.is_Pow:
        b, ex = e.args
        c = None # records sign of b if b is +/-z or has a bounded value
        if b.is_Mul:
            c, b = b.as_two_terms()
            if c is S.NegativeOne and b == z:
                c = '-'
        elif b == z:
            c = '+'

        if ex.is_number:
            if c is None:
                base = b.subs(z, z0)
                if base.is_bounded and (ex.is_bounded or base is not S.One):
                    return base**ex
            else:
                if z0 == 0 and ex < 0:
                    if dir != c:
                        # integer
                        if ex.is_even:
                            return S.Infinity
                        elif ex.is_odd:
                            return S.NegativeInfinity
                        # rational
                        elif ex.is_Rational:
                            return (S.NegativeOne**ex)*S.Infinity
                        else:
                            return S.ComplexInfinity
                    return S.Infinity
                return z0**ex

    if e.is_Mul or not z0 and e.is_Pow and b.func is log:
        if e.is_Mul:
            # weed out the z-independent terms
            i, d = e.as_independent(z)
            if i is not S.One and i.is_bounded:
                return i*limit(d, z, z0, dir)
        else:
            i, d = S.One, e
        if not z0:
            # look for log(z)**q or z**p*log(z)**q
            p, q = Wild("p"), Wild("q")
            r = d.match(z**p * log(z)**q)
            if r:
                p, q = [r.get(w, w) for w in [p, q]]
                if q and q.is_number and p.is_number:
                    if q > 0:
                        if p > 0:
                            return S.Zero
                        else:
                            return -oo*i
                    else:
                        if p >= 0:
                            return S.Zero
                        else:
                            return -oo*i

    if e.is_Add:
        if e.is_polynomial() and not z0.is_unbounded:
            return Add(*[limit(term, z, z0, dir) for term in e.args])

        # this is a case like limit(x*y+x*z, z, 2) == x*y+2*x
        # but we need to make sure, that the general gruntz() algorithm is
        # executed for a case like "limit(sqrt(x+1)-sqrt(x),x,oo)==0"
        unbounded = []; unbounded_result=[]
        finite = []; unknown = []
        ok = True
        for term in e.args:
            if not term.has(z) and not term.is_unbounded:
                finite.append(term)
                continue
            result = term.subs(z, z0)
            bounded = result.is_bounded
            if bounded is False or result is S.NaN:
                if unknown:
                    ok = False
                    break
                unbounded.append(term)
                if result != S.NaN:
                    # take result from direction given
                    result = limit(term, z, z0, dir)
                unbounded_result.append(result)
            elif bounded:
                finite.append(result)
            else:
                if unbounded:
                    ok = False
                    break
                unknown.append(result)
        if not ok:
            # we won't be able to resolve this with unbounded
            # terms, e.g. Sum(1/k, (k, 1, n)) - log(n) as n -> oo:
            # since the Sum is unevaluated it's boundedness is
            # unknown and the log(n) is oo so you get Sum - oo
            # which is unsatisfactory.
            raise NotImplementedError('unknown boundedness for %s' %
                                      (unknown or result))
        u = Add(*unknown)
        if unbounded:
            inf_limit = Add(*unbounded_result)
            if inf_limit is not S.NaN:
                return inf_limit + u
            if finite:
                return Add(*finite) + limit(Add(*unbounded), z, z0, dir) + u
        else:
            return Add(*finite) + u

    if e.is_Order:
        args = e.args
        return C.Order(limit(args[0], z, z0), *args[1:])

    try:
        r = gruntz(e, z, z0, dir)
        if r is S.NaN:
            raise PoleError()
    except PoleError:
        r = heuristics(e, z, z0, dir)
    return r

def heuristics(e, z, z0, dir):
    if z0 == oo:
        return limit(e.subs(z, 1/z), z, sympify(0), "+")
    elif e.is_Mul:
        r = []
        for a in e.args:
            if not a.is_bounded:
                r.append(a.limit(z, z0, dir))
        if r:
            return Mul(*r)
    elif e.is_Add:
        r = []
        for a in e.args:
            r.append(a.limit(z, z0, dir))
        return Add(*r)
    elif e.is_Function:
        return e.subs(e.args[0], limit(e.args[0], z, z0, dir))
    msg = "Don't know how to calculate the limit(%s, %s, %s, dir=%s), sorry."
    raise PoleError(msg % (e, z, z0, dir))


class Limit(Expr):
    """Represents an unevaluated limit.

    Examples:

    >>> from sympy import Limit, sin, Symbol
    >>> from sympy.abc import x
    >>> Limit(sin(x)/x, x, 0)
    Limit(sin(x)/x, x, 0)
    >>> Limit(1/x, x, 0, dir="-")
    Limit(1/x, x, 0, dir='-')

    """

    def __new__(cls, e, z, z0, dir="+"):
        e = sympify(e)
        z = sympify(z)
        z0 = sympify(z0)
        obj = Expr.__new__(cls)
        obj._args = (e, z, z0, dir)
        return obj

    def doit(self, **hints):
        e, z, z0, dir = self.args
        if hints.get('deep', True):
            e = e.doit(**hints)
            z = z.doit(**hints)
            z0 = z0.doit(**hints)
        return limit(e, z, z0, dir)