public void GearTest6c() { for (int exponent = 2; exponent <= 5; exponent++) { // evaluating y' = 3 y/ t solution y = t^exponent var ode = new GearsBDF(); ode.Initialize( 1, new double[] { 1 }, (t, y, dydt) => { dydt[0] = exponent * y[0] / t; }, new GearsBDFOptions { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); var sp = new double[1]; double tres; for (double ii = 0; ii <= 6000; ii += 1) { double time = Math.Pow(10, ii / 1000.0); ode.Evaluate(time, sp); var y0_expected = RMath.Pow(time, exponent); Assert.AreEqual(y0_expected, sp[0], 1E-6 * y0_expected + 1E-7); } } }
public void GearTest6a() { for (int exponent = 2; exponent <= 5; exponent++) { // evaluating y' = 3 y/ t solution y = t^exponent var ode = new GearsBDF(); ode.Initialize( 1, new double[] { 1 }, (t, y, dydt) => { dydt[0] = exponent * y[0] / t; }, new GearsBDFOptions { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); var sp = new double[1]; double tres; do { ode.Evaluate(out tres, sp); var y0_expected = RMath.Pow(tres, exponent); Assert.AreEqual(y0_expected, sp[0], 1E-6 * y0_expected + 1E-7); } while (tres < 1e6); } }
public void GearTestSparse03() { var ode = new GearsBDF(); var numberOfCells = 100; var initY = new double[numberOfCells]; for (int i = 0; i < numberOfCells; ++i) { initY[i] = 0; // initally zero concentration } // Symmetrical problem, diffusion from both sides of a plate var f = new Action <double, double[], double[]>((t, y, dydt) => { double yim1 = 1; // outer concentration at lower index double yip1 = 1; // outer concentration at upper index int lend = y.Length - 1; int i = 0; dydt[0] = y[i + 1] - 2 * y[i] + yim1; for (i = 1; i < lend; ++i) { dydt[i] = y[i + 1] - 2 * y[i] + y[i - 1]; } dydt[i] = yip1 - 2 * y[i] + y[i - 1]; } ); ode.InitializeSparse( 0, initY, f, null, new GearsBDFOptions { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); int nCounter = 0; var sp = new double[numberOfCells]; double tres = 0; for (; tres <= 10000;) { ode.Evaluate(out tres, sp); double t = tres; for (int i = 0; i < numberOfCells; ++i) { Assert.AreEqual(sp[i], sp[numberOfCells - 1 - i], 1E-7 * sp[i] + 1E-8); // test for symmetry of the solution } ++nCounter; } }
public void GearTest7b() { Vector fuu(double t, Vector y) { return(new Vector(y[0] * y[0])); } var pulse = Altaxo.Calc.Ode.Ode.GearBDF( 0, new Vector(1 / 64.0), fuu, new Altaxo.Calc.Ode.Options { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); // evaluating y' = y², y[0]=1/64 var ode = new GearsBDF(); ode.Initialize( 0, // t0=0 new double[] { 1.0 / 64 }, // y0=1/64 (t, y, dydt) => { dydt[0] = y[0] * y[0]; }, new GearsBDFOptions { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); var sp = new double[1]; foreach (var spulse in pulse.SolveTo(32)) { ode.Evaluate(out var tres, sp); Assert.AreEqual(spulse.T, tres); Assert.AreEqual(spulse.X[0], sp[0]); var y0_expected = 1 / (64 - tres); Assert.AreEqual(y0_expected, spulse.X[0], 1E-6 * y0_expected + 1E-7); Assert.AreEqual(y0_expected, sp[0], 1E-6 * y0_expected + 1E-7); } ; }
public void GearTestSparse01() { const double lambda1 = -1; const double lambda2 = -1000; const double lambda1PlusLambda2By2 = (lambda1 + lambda2) / 2; const double lambda1MinusLambda2By2 = (lambda1 - lambda2) / 2; const double C1 = 1; const double C2 = 1; var ode = new GearsBDF(); ode.InitializeSparse( 0, new double[] { C1 + C2, C1 - C2 }, (t, y, dydt) => { dydt[0] = lambda1PlusLambda2By2 * y[0] + lambda1MinusLambda2By2 * y[1]; dydt[1] = lambda1MinusLambda2By2 * y[0] + lambda1PlusLambda2By2 * y[1]; }, null, new GearsBDFOptions { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); int nCounter = 0; var sp = new double[2]; double tres = 0; for (; tres <= 20;) { ode.Evaluate(out tres, sp); double t = tres; var y0_expected = C1 * Math.Exp(lambda1 * t) + C2 * Math.Exp(lambda2 * t); var y1_expected = C1 * Math.Exp(lambda1 * t) - C2 * Math.Exp(lambda2 * t); Assert.AreEqual(y0_expected, sp[0], 1E-7 * y0_expected + 1E-8); Assert.AreEqual(y1_expected, sp[1], 6E-7 * y1_expected + 1E-8); ++nCounter; } }
public void GearTest3a() { Vector fuu(double t, Vector y) { return(new Vector(y[0] / t)); } var pulse = Altaxo.Calc.Ode.Ode.GearBDF( 1, new Vector(1), fuu, new Altaxo.Calc.Ode.Options { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); var ode = new GearsBDF(); ode.Initialize( 1, new double[] { 1 }, (t, y, dydt) => { dydt[0] = y[0] / t; }, new GearsBDFOptions { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); var sp = new double[1]; foreach (var spulse in pulse.SolveTo(100000)) { double t = spulse.T; ode.Evaluate(out var tsp, sp); Assert.AreEqual(t, tsp, 1e-4); var y0_expected = t; Assert.AreEqual(y0_expected, sp[0], 1E-3 * y0_expected + 1E-4); } }
public void GearTest7a() { // evaluating y' = 1/y, y[0]=1/64 var ode = new GearsBDF(); ode.Initialize( 0, // t0=0 new double[] { 1.0 / 64 }, // y0=1/64 (t, y, dydt) => { dydt[0] = 1 / y[0]; }, new GearsBDFOptions { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); var sp = new double[1]; double tres; do { ode.Evaluate(out tres, sp); var y0_expected = Math.Sqrt(1 + 8192 * tres) / 64; Assert.AreEqual(y0_expected, sp[0], 1E-6 * y0_expected + 1E-7); } while (tres < 1e6); }
public void GearTest5a() { // evaluating y' = 3 y/ t solution y = t³ var ode = new GearsBDF(); ode.Initialize( 1, new double[] { 1 }, (t, y, dydt) => { dydt[0] = 3 * y[0] / t; }, new GearsBDFOptions { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); var sp = new double[1]; double tres; do { ode.Evaluate(out tres, sp); var y0_expected = tres * tres * tres; Assert.AreEqual(y0_expected, sp[0], 1E-6 * y0_expected + 1E-7); } while (tres < 1e6); }
public void GearTestSparse02() { const double lambda1 = -1; const double lambda2 = -1000; const double lambda1PlusLambda2By2 = (lambda1 + lambda2) / 2; const double lambda1MinusLambda2By2 = (lambda1 - lambda2) / 2; const double C1 = 1; const double C2 = 1; var ode = new GearsBDF(); var numberOfCells = 100; var initY = new double[numberOfCells * 2]; for (int i = 0; i < numberOfCells; ++i) { initY[i * 2 + 0] = C1 + C2; initY[i * 2 + 1] = C1 - C2; } var f = new Action <double, double[], double[]>((t, y, dydt) => { for (int i = 0; i < y.Length; i += 2) { dydt[i] = lambda1PlusLambda2By2 * y[i] + lambda1MinusLambda2By2 * y[i + 1]; dydt[i + 1] = lambda1MinusLambda2By2 * y[i] + lambda1PlusLambda2By2 * y[i + 1]; } } ); ode.InitializeSparse( 0, initY, f, null, new GearsBDFOptions { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); int nCounter = 0; var sp = new double[numberOfCells * 2]; double tres = 0; for (; tres <= 20;) { ode.Evaluate(out tres, sp); double t = tres; var y0_expected = C1 * Math.Exp(lambda1 * t) + C2 * Math.Exp(lambda2 * t); var y1_expected = C1 * Math.Exp(lambda1 * t) - C2 * Math.Exp(lambda2 * t); for (int i = 0; i < numberOfCells; ++i) { Assert.AreEqual(y0_expected, sp[i * 2 + 0], 1E-7 * y0_expected + 1E-8); Assert.AreEqual(y1_expected, sp[i * 2 + 1], 6E-7 * y1_expected + 1E-8); } ++nCounter; } }
public void GearTest2a() { const double lambda1 = -1; const double lambda2 = -1000; const double lambda1PlusLambda2By2 = (lambda1 + lambda2) / 2; const double lambda1MinusLambda2By2 = (lambda1 - lambda2) / 2; const double C1 = 1; const double C2 = 1; Vector fuu(double t, Vector y) { return(new Vector(lambda1PlusLambda2By2 * y[0] + lambda1MinusLambda2By2 * y[1], lambda1MinusLambda2By2 * y[0] + lambda1PlusLambda2By2 * y[1])); } var pulse = Altaxo.Calc.Ode.Ode.GearBDF( 0, new Vector(C1 + C2, C1 - C2), fuu, new Altaxo.Calc.Ode.Options { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); var ode = new GearsBDF(); ode.Initialize( 0, new double[] { C1 + C2, C1 - C2 }, (t, y, dydt) => { dydt[0] = lambda1PlusLambda2By2 * y[0] + lambda1MinusLambda2By2 * y[1]; dydt[1] = lambda1MinusLambda2By2 * y[0] + lambda1PlusLambda2By2 * y[1]; }, new GearsBDFOptions { RelativeTolerance = 1e-7, AbsoluteTolerance = 1E-8 }); int nCounter = 0; var sp = new double[2]; var pulseit = pulse.SolveTo(20).GetEnumerator(); for (; ;) { if (!pulseit.MoveNext()) { break; } var spulse = pulseit.Current; ode.Evaluate(out var tres, sp); Assert.AreEqual(spulse.T, tres); Assert.AreEqual(spulse.X[0], sp[0]); Assert.AreEqual(spulse.X[1], sp[1]); double t = spulse.T; var y0_expected = C1 * Math.Exp(lambda1 * t) + C2 * Math.Exp(lambda2 * t); var y1_expected = C1 * Math.Exp(lambda1 * t) - C2 * Math.Exp(lambda2 * t); Assert.AreEqual(y0_expected, spulse.X[0], 1E-7 * y0_expected + 1E-8); Assert.AreEqual(y1_expected, spulse.X[1], 6E-7 * y1_expected + 1E-8); t = tres; y0_expected = C1 * Math.Exp(lambda1 * t) + C2 * Math.Exp(lambda2 * t); y1_expected = C1 * Math.Exp(lambda1 * t) - C2 * Math.Exp(lambda2 * t); Assert.AreEqual(y0_expected, sp[0], 1E-7 * y0_expected + 1E-8); Assert.AreEqual(y1_expected, sp[1], 6E-7 * y1_expected + 1E-8); ++nCounter; } }