Browse Source

Change API of dsp/ode.hpp

tags/v0.6.2b
Andrew Belt 6 years ago
parent
commit
ad6721918a
2 changed files with 36 additions and 12 deletions
  1. +34
    -10
      include/dsp/ode.hpp
  2. +2
    -2
      include/util/common.hpp

+ 34
- 10
include/dsp/ode.hpp View File

@@ -3,10 +3,14 @@


namespace rack { namespace rack {


typedef void (*stepCallback)(float x, const float y[], float dydt[]);
/** The callback function `f` in each of these stepping functions must have the signature
void f(float x, const float y[], float dydt[])
A capturing lambda is ideal for this.
*/


/** Solve an ODE system using the 1st order Euler method */
inline void stepEuler(stepCallback f, float x, float dx, float y[], int len) {
/** Solves an ODE system using the 1st order Euler method */
template<typename F>
void stepEuler(float x, float dx, float y[], int len, F f) {
float k[len]; float k[len];


f(x, y, k); f(x, y, k);
@@ -15,8 +19,28 @@ inline void stepEuler(stepCallback f, float x, float dx, float y[], int len) {
} }
} }


/** Solve an ODE system using the 4th order Runge-Kutta method */
inline void stepRK4(stepCallback f, float x, float dx, float y[], int len) {
/** Solves an ODE system using the 2nd order Runge-Kutta method */
template<typename F>
void stepRK2(float x, float dx, float y[], int len, F f) {
float k1[len];
float k2[len];
float yi[len];

f(x, y, k1);

for (int i = 0; i < len; i++) {
yi[i] = y[i] + k1[i] * dx / 2.f;
}
f(x + dx / 2.f, yi, k2);

for (int i = 0; i < len; i++) {
y[i] += dx * k2[i];
}
}

/** Solves an ODE system using the 4th order Runge-Kutta method */
template<typename F>
void stepRK4(float x, float dx, float y[], int len, F f) {
float k1[len]; float k1[len];
float k2[len]; float k2[len];
float k3[len]; float k3[len];
@@ -26,14 +50,14 @@ inline void stepRK4(stepCallback f, float x, float dx, float y[], int len) {
f(x, y, k1); f(x, y, k1);


for (int i = 0; i < len; i++) { for (int i = 0; i < len; i++) {
yi[i] = y[i] + k1[i] * dx / 2.0;
yi[i] = y[i] + k1[i] * dx / 2.f;
} }
f(x + dx / 2.0, yi, k2);
f(x + dx / 2.f, yi, k2);


for (int i = 0; i < len; i++) { for (int i = 0; i < len; i++) {
yi[i] = y[i] + k2[i] * dx / 2.0;
yi[i] = y[i] + k2[i] * dx / 2.f;
} }
f(x + dx / 2.0, yi, k3);
f(x + dx / 2.f, yi, k3);


for (int i = 0; i < len; i++) { for (int i = 0; i < len; i++) {
yi[i] = y[i] + k3[i] * dx; yi[i] = y[i] + k3[i] * dx;
@@ -41,7 +65,7 @@ inline void stepRK4(stepCallback f, float x, float dx, float y[], int len) {
f(x + dx, yi, k4); f(x + dx, yi, k4);


for (int i = 0; i < len; i++) { for (int i = 0; i < len; i++) {
y[i] += dx * (k1[i] + 2.0 * k2[i] + 2.0 * k3[i] + k4[i]) / 6.0;
y[i] += dx * (k1[i] + 2.f * k2[i] + 2.f * k3[i] + k4[i]) / 6.f;
} }
} }




+ 2
- 2
include/util/common.hpp View File

@@ -116,14 +116,14 @@ Example:
fclose(file); fclose(file);
}); });
*/ */
template <typename F>
template<typename F>
struct DeferWrapper { struct DeferWrapper {
F f; F f;
DeferWrapper(F f) : f(f) {} DeferWrapper(F f) : f(f) {}
~DeferWrapper() { f(); } ~DeferWrapper() { f(); }
}; };


template <typename F>
template<typename F>
DeferWrapper<F> deferWrapper(F f) { DeferWrapper<F> deferWrapper(F f) {
return DeferWrapper<F>(f); return DeferWrapper<F>(f);
} }


Loading…
Cancel
Save