(b, Q, n, DE)
Parametric Poly Risch Differential Equation - No cancellation: deg(b) small enough.

    Given a derivation D on k[t], n in ZZ, and b, q1, ..., qm in k[t] with
    deg(b) < deg(D) - 1 and either D == d/dt or deg(D) >= 2, returns
    h1, ..., hr in k[t] and a matrix A with coefficients in Const(k) such that
    if c1, ..., cm in Const(k) and q in k[t] satisfy deg(q) <= n and
    Dq + b*q == Sum(ci*qi, (i, 1, m)) then q = Sum(dj*hj, (j, 1, r)) where
    d1, ..., dr in Const(k) and A*Matrix([[c1, ..., cm, d1, ..., dr]]).T == 0.
Parametric Poly Risch Differential Equation - No cancellation: deg(b) small enough.
Parametric Poly Risch Differential Equation - No cancellation : deg ( b ) small enough .
def prde_no_cancel_b_small(b, Q, n, DE):
    """
    Parametric Poly Risch Differential Equation - No cancellation: deg(b) small enough.

    Given a derivation D on k[t], n in ZZ, and b, q1, ..., qm in k[t] with
    deg(b) < deg(D) - 1 and either D == d/dt or deg(D) >= 2, returns
    h1, ..., hr in k[t] and a matrix A with coefficients in Const(k) such that
    if c1, ..., cm in Const(k) and q in k[t] satisfy deg(q) <= n and
    Dq + b*q == Sum(ci*qi, (i, 1, m)) then q = Sum(dj*hj, (j, 1, r)) where
    d1, ..., dr in Const(k) and A*Matrix([[c1, ..., cm, d1, ..., dr]]).T == 0.
    """
    m = len(Q)
    H = [Poly(0, DE.t)]*m

    for N in xrange(n, 0, -1):  # [n, ..., 1]
        for i in range(m):
            si = Q[i].nth(N + DE.d.degree(DE.t) - 1)/(N*DE.d.LC())
            sitn = Poly(si*DE.t**N, DE.t)
            H[i] = H[i] + sitn
            Q[i] = Q[i] - derivation(sitn, DE) - b*sitn

    if b.degree(DE.t) > 0:
        for i in range(m):
            si = Poly(Q[i].nth(b.degree(DE.t))/b.LC(), DE.t)
            H[i] = H[i] + si
            Q[i] = Q[i] - derivation(si, DE) - b*si
        if all(qi.is_zero for qi in Q):
            dc = -1
            M = Matrix()
        else:
            dc = max([qi.degree(DE.t) for qi in Q])
            M = Matrix(dc + 1, m, lambda i, j: Q[j].nth(i))
        A, u = constant_system(M, zeros(dc + 1, 1), DE)
        c = eye(m)
        A = A.row_join(zeros(A.rows, m)).col_join(c.row_join(-c))
        return (H, A)
    else:
        # TODO: implement this (requires recursive param_rischDE() call)
        raise NotImplementedError
def prde_no_cancel_b_small ( b , Q , n , DE ) : m = len ( Q ) H = [ Poly ( 0 , DE . t ) ] * m for N in xrange ( n , 0 , - 1 ) : # [n, ..., 1] for i in range ( m ) : si = Q [ i ] . nth ( N + DE . d . degree ( DE . t ) - 1 ) / ( N * DE . d . LC ( ) ) sitn = Poly ( si * DE . t ** N , DE . t ) H [ i ] = H [ i ] + sitn Q [ i ] = Q [ i ] - derivation ( sitn , DE ) - b * sitn if b . degree ( DE . t ) > 0 : for i in range ( m ) : si = Poly ( Q [ i ] . nth ( b . degree ( DE . t ) ) / b . LC ( ) , DE . t ) H [ i ] = H [ i ] + si Q [ i ] = Q [ i ] - derivation ( si , DE ) - b * si if all ( qi . is_zero for qi in Q ) : dc = - 1 M = Matrix ( ) else : dc = max ( [ qi . degree ( DE . t ) for qi in Q ] ) M = Matrix ( dc + 1 , m , lambda i , j : Q [ j ] . nth ( i ) ) A , u = constant_system ( M , zeros ( dc + 1 , 1 ) , DE ) c = eye ( m ) A = A . row_join ( zeros ( A . rows , m ) ) . col_join ( c . row_join ( - c ) ) return ( H , A ) else : # TODO: implement this (requires recursive param_rischDE() call) raise NotImplementedError