Search code examples
pythonsympydifferential-equations

How to find the nth derivative given the first derivative with SymPy?


Given some f and the differential equation x'(t) = f(x(t)), how do I compute x(n)(t) in terms of x(t)?

For example, given f(x(t)) = sin(x(t)), I want to obtain x(3)(t) = (cos(x(t))2 − sin(x(t))2) sin(x(t)).

So far I've tried

>>> from sympy import diff, sin
>>> from sympy.abc import x, t
>>> diff(sin(x(t)), t, 2)

which gives me

-sin(x(t))*Derivative(x(t), t)**2 + cos(x(t))*Derivative(x(t), t, t)

but I'm not sure how to tell SymPy what Derivative(x(t), t) is and have it figure out Derivative(x(t), t, t), etc. automatically.


Answer:

Here's my final solution based on the answers I received below:

def diff(x_derivs_known, t, k, simplify=False):
    try: n = len(x_derivs_known)
    except TypeError: n = None
    if n is None:
        result = sympy.diff(x_derivs_known, t, k)
        if simplify: result = result.simplify()
    elif k < n:
        result = x_derivs_known[k]
    else:
        i = n - 1
        result = x_derivs_known[i]
        while i < k:
            result = result.diff(t)
            j = len(x_derivs_known)
            x0 = None
            while j > 1:
                j -= 1
                result = result.subs(sympy.Derivative(x_derivs_known[0], t, j), x_derivs_known[j])
            i += 1
            if simplify: result = result.simplify()
    return result

Example:

>>> diff((x(t), sympy.sin(x(t))), t, 3, True)
sin(x(t))*cos(2*x(t))

Solution

  • Here is one approach that returns a list of all derivatives up to n-th order

    import sympy as sp
    
    x = sp.Function('x')
    t = sp.symbols('t')
    
    f = lambda x: x**2 #sp.exp, sp.sin
    n = 4 #3, 4, 5
    
    deriv_list = [x(t), f(x(t))]  # list of derivatives [x(t), x'(t), x''(t),...]
    for i in range(1,n):
        df_i = deriv_list[-1].diff(t).replace(sp.Derivative,lambda *args: f(x(t)))
        deriv_list.append(df_i)
    
    print(deriv_list)
    

    [x(t), x(t)**2, 2*x(t)**3, 6*x(t)**4, 24*x(t)**5]

    With f=sp.sin it returns

     [x(t), sin(x(t)), sin(x(t))*cos(x(t)), -sin(x(t))**3 + sin(x(t))*cos(x(t))**2, -5*sin(x(t))**3*cos(x(t)) + sin(x(t))*cos(x(t))**3]
    

    EDIT: A recursive function for the computation of the n-th derivative:

    def der_xt(f, n):
        if n==1:
            return f(x(t))
        else:
            return der_xt(f,n-1).diff(t).replace(sp.Derivative,lambda *args: f(x(t)))
    
    print(der_xt(sp.sin,3))
    

    -sin(x(t))**3 + sin(x(t))*cos(x(t))**2