def runge_kutta_ode_solver(ode, time_step, y, params):
    """4th order Runge-Kutta ODE solver.

    Carnahan, B., Luther, H. A., and Wilkes, J. O. (1969).
    Applied Numerical Methods. Wiley, New York.

    Parameters
    ----------
    ode : function
        Ordinary differential equation function. In the Lorenz model it is SDE.
    time_step : float
    y : np.ndarray of dimension (batch_size, n_obs)
        Current state of the time-series.
    params : list of parameters
        The parameters needed to evaluate the ode. In this case it is
        list of four elements - eta, theta1, theta2 and f.

    Returns
    -------
    np.ndarray
        Resulting state initiated at y and satisfying ode solved by this solver.

    """
    k1 = time_step * ode(y, params)

    k2 = time_step * ode(y + k1 / 2, params)

    k3 = time_step * ode(y + k2 / 2, params)

    k4 = time_step * ode(y + k3, params)

    y = y + (k1 + 2 * k2 + 2 * k3 + k4) / 6

    return y