#NEWLINE# def parametric_log_deriv_heu( fa , fd , wa , wd , DE , c1 = None ) : #NEWLINE# #INDENT# '\n    Parametric logarithmic derivative heuristic.\n\n    Given a derivation D on k[t], f in k(t), and a hyperexponential monomial\n    theta over k(t), raises either NotImplementedError, in which case the\n    heuristic failed, or returns None, in which case it has proven that no\n    solution exists, or returns a solution (n, m, v) of the equation\n    n*f == Dv/v + m*Dtheta/theta, with v in k(t)* and n, m in ZZ with n != 0.\n\n    If this heuristic fails, the structure theorem approach will need to be\n    used.\n\n    The argument w == Dtheta/theta\n    ' #NEWLINE# c1 = ( c1 or Dummy ( 'c1' ) ) #NEWLINE# ( p , a ) = fa . div ( fd ) #NEWLINE# ( q , b ) = wa . div ( wd ) #NEWLINE# B = max ( 0 , ( derivation ( DE . t , DE ) . degree ( DE . t ) - 1 ) ) #NEWLINE# C = max ( p . degree ( DE . t ) , q . degree ( DE . t ) ) #NEWLINE# if ( q . degree ( DE . t ) > B ) : #NEWLINE# #INDENT# eqs = [ ( p . nth ( i ) - ( c1 * q . nth ( i ) ) ) for i in range ( ( N + 1 ) , ( C + 1 ) ) ] #NEWLINE# s = solve ( eqs , c1 ) #NEWLINE# if ( ( not s ) or ( not s [ c1 ] . is_Rational ) ) : #NEWLINE# #INDENT# return None #NEWLINE# #UNINDENT# ( N , M ) = s [ c1 ] . as_numer_denom ( ) #NEWLINE# ( N , M ) = ( Poly ( N , DE . t ) , Poly ( M , DE . t ) ) #NEWLINE# nfmwa = ( ( ( N * fa ) * wd ) - ( ( M * wa ) * fd ) ) #NEWLINE# nfmwd = ( fd * wd ) #NEWLINE# Qv = is_log_deriv_k_t_radical_in_field ( ( ( ( N * fa ) * wd ) - ( ( M * wa ) * fd ) ) , ( fd * wd ) , DE , 'auto' ) #NEWLINE# if ( Qv is None ) : #NEWLINE# #INDENT# return None #NEWLINE# #UNINDENT# ( Q , e , v ) = Qv #NEWLINE# if ( e != 1 ) : #NEWLINE# #INDENT# return None #NEWLINE# #UNINDENT# if ( Q . is_zero or v . is_zero ) : #NEWLINE# #INDENT# return None #NEWLINE# #UNINDENT# return ( ( Q * N ) , ( Q * M ) , v ) #NEWLINE# #UNINDENT# if ( p . degree ( DE . t ) > B ) : #NEWLINE# #INDENT# return None #NEWLINE# #UNINDENT# c = lcm ( fd . as_poly ( DE . t ) . LC ( ) , wd . as_poly ( DE . t ) . LC ( ) ) #NEWLINE# l = ( fd . monic ( ) . lcm ( wd . monic ( ) ) * Poly ( c , DE . t ) ) #NEWLINE# ( ln , ls ) = splitfactor ( l , DE ) #NEWLINE# z = ( ls * ln . gcd ( ln . diff ( DE . t ) ) ) #NEWLINE# if ( not z . has ( DE . t ) ) : #NEWLINE# #INDENT# raise NotImplementedError ( 'parametric_log_deriv_heu() heuristic failed: z in k.' ) #NEWLINE# #UNINDENT# ( u1 , r1 ) = ( fa * l . quo ( fd ) ) . div ( z ) #NEWLINE# ( u2 , r2 ) = ( wa * l . quo ( wd ) ) . div ( z ) #NEWLINE# eqs = [ ( r1 . nth ( i ) - ( c1 * r2 . nth ( i ) ) ) for i in range ( z . degree ( DE . t ) ) ] #NEWLINE# s = solve ( eqs , c1 ) #NEWLINE# if ( ( not s ) or ( not s [ c1 ] . is_Rational ) ) : #NEWLINE# #INDENT# return None #NEWLINE# #UNINDENT# ( M , N ) = s [ c1 ] . as_numer_denom ( ) #NEWLINE# nfmwa = ( ( ( N . as_poly ( DE . t ) * fa ) * wd ) - ( ( M . as_poly ( DE . t ) * wa ) * fd ) ) #NEWLINE# nfmwd = ( fd * wd ) #NEWLINE# Qv = is_log_deriv_k_t_radical_in_field ( nfmwa , nfmwd , DE ) #NEWLINE# if ( Qv is None ) : #NEWLINE# #INDENT# return None #NEWLINE# #UNINDENT# ( Q , v ) = Qv #NEWLINE# if ( Q . is_zero or v . is_zero ) : #NEWLINE# #INDENT# return None #NEWLINE# #UNINDENT# return ( ( Q * N ) , ( Q * M ) , v )