Ejemplo n.º 1
0
        /// <summary>
        /// Solves an ODE using RK2
        /// </summary>
        /// <param name="initial"></param>
        /// <param name="x"></param>
        /// <param name="h"></param>
        /// <param name="system"></param>
        /// <returns></returns>
        private static float[] SolveRK2(float[] initial, float x, float h, CalculateDerivativesHandler calculateDerivatives)
        {
            // do Euler step with half the step value
            float[] k1 = calculateDerivatives(initial, x);
            float[] temp = DoEulerStep(initial, k1, h / 2.0f);

            // calculate again at midpoint
            float[] k2 = calculateDerivatives(temp, x + (h / 2.0f));

            // use derivatives for complete timestep
            return DoEulerStep(initial, k2, h);
        }
Ejemplo n.º 2
0
        /// <summary>
        /// This method solves first-order ODEs. It is passed an array
        /// of dependent variables in "array" at x, and returns an
        /// array of new values at x + h.
        /// </summary>
        /// <param name="initial">Array of initial values</param>
        /// <param name="x">Initial value of x (usually time)</param>
        /// <param name="h">Increment value for x (usually delta time)</param>
        /// <param name="system">Class containing a method to calculate the
        /// derivatives of the initial values</param>
        /// <param name="integrator">Type of numeric
        /// integration to use</param>
        /// <returns></returns>
        public static float[] Solve(float[] initial, float x, float h,
			CalculateDerivativesHandler calculateDerivatives,
			Integrator integrator)
        {
            switch (integrator)
            {
                case Integrator.Euler :
                    return SolveEuler(initial, x, h, calculateDerivatives);
                case Integrator.RK2 :
                    return SolveRK2(initial, x, h, calculateDerivatives);
                case Integrator.RK4 :
                    goto default;
                default :
                    return SolveRK4(initial, x, h, calculateDerivatives);
            }
        }
Ejemplo n.º 3
0
 /// <summary>
 /// Solves an ODE using Euler integration
 /// </summary>
 /// <param name="initial"></param>
 /// <param name="x"></param>
 /// <param name="h"></param>
 /// <param name="system"></param>
 /// <returns></returns>
 private static float[] SolveEuler(float[] initial, float x, float h, CalculateDerivativesHandler calculateDerivatives)
 {
     // final = initial + derived * h
     float[] derivs = calculateDerivatives(initial, x);
     return DoEulerStep(initial, derivs, h);
 }
Ejemplo n.º 4
0
        /// <summary>
        /// Solves an ODE using RK4
        /// </summary>
        /// <param name="initial"></param>
        /// <param name="x"></param>
        /// <param name="h"></param>
        /// <param name="system"></param>
        /// <returns></returns>
        private static float[] SolveRK4(float[] initial, float x, float h, CalculateDerivativesHandler calculateDerivatives)
        {
            float[] k1 = calculateDerivatives(initial, x);
            float[] temp = DoEulerStep(initial, k1, h / 2.0f);

            float[] k2 = calculateDerivatives(temp, x + (h / 2.0f));
            temp = DoEulerStep(initial, k2, h / 2.0f);

            float[] k3 = calculateDerivatives(temp, x + (h / 2.0f));
            temp = DoEulerStep(initial, k3, h);

            float[] k4 = calculateDerivatives(temp, x + h);

            float[] ret = DoEulerStep(initial, k1, h / 6.0f);
            ret = DoEulerStep(ret, k2, h / 3.0f);
            ret = DoEulerStep(ret, k3, h / 3.0f);
            ret = DoEulerStep(ret, k4, h / 6.0f);
            return ret;
        }