From e3230801c9e9dd0eb2ac2f444820ed683eac2411 Mon Sep 17 00:00:00 2001 From: arghdos Date: Thu, 6 Dec 2018 10:57:18 -0500 Subject: [PATCH] Expose getting/setting of max-steps to python interface & test --- include/cantera/numerics/CVodesIntegrator.h | 1 + include/cantera/numerics/Integrator.h | 11 +++++++++++ include/cantera/zeroD/ReactorNet.h | 15 +++++++++++++++ interfaces/cython/cantera/_cantera.pxd | 2 ++ interfaces/cython/cantera/reactor.pyx | 10 ++++++++++ interfaces/cython/cantera/test/test_reactor.py | 16 ++++++++++++++++ src/numerics/CVodesIntegrator.cpp | 5 +++++ 7 files changed, 60 insertions(+) diff --git a/include/cantera/numerics/CVodesIntegrator.h b/include/cantera/numerics/CVodesIntegrator.h index 290054cc9..1c2c1d5c8 100644 --- a/include/cantera/numerics/CVodesIntegrator.h +++ b/include/cantera/numerics/CVodesIntegrator.h @@ -53,6 +53,7 @@ public: virtual void setMaxStepSize(double hmax); virtual void setMinStepSize(double hmin); virtual void setMaxSteps(int nmax); + virtual int maxSteps(); virtual void setMaxErrTestFails(int n); virtual void setBandwidth(int N_Upper, int N_Lower) { m_mupper = N_Upper; diff --git a/include/cantera/numerics/Integrator.h b/include/cantera/numerics/Integrator.h index 31c7d7471..6e0cdfc2c 100644 --- a/include/cantera/numerics/Integrator.h +++ b/include/cantera/numerics/Integrator.h @@ -183,10 +183,21 @@ public: warn("setMaxErrTestFails"); } + //! Set the maximum number of time-steps the integrator can take + //! before reaching the next output time + //! @param nmax The maximum number of steps, setting this value + //! to zero disables this option. virtual void setMaxSteps(int nmax) { warn("setMaxStep"); } + //! Returns the maximum number of time-steps the integrator can take + //! before reaching the next output time + virtual int maxSteps() { + warn("maxSteps"); + return 0; + } + virtual void setBandwidth(int N_Upper, int N_Lower) { warn("setBandwidth"); } diff --git a/include/cantera/zeroD/ReactorNet.h b/include/cantera/zeroD/ReactorNet.h index 8399c5514..dedd8e1d2 100644 --- a/include/cantera/zeroD/ReactorNet.h +++ b/include/cantera/zeroD/ReactorNet.h @@ -207,6 +207,21 @@ public: m_integrator_init = false; } + //! Set the maximum number of internal integration time-steps the + //! integrator will take before reaching the next output time + //! @param nmax The maximum number of steps, setting this value + //! to zero disables this option. + virtual void setMaxSteps(int nmax) { + m_integ->setMaxSteps(nmax); + } + + //! Returns the maximum number of internal integration time-steps the + //! integrator will take before reaching the next output time + //! + virtual int maxSteps() { + return m_integ->maxSteps(); + } + protected: //! Initialize the reactor network. Called automatically the first time //! advance or step is called. diff --git a/interfaces/cython/cantera/_cantera.pxd b/interfaces/cython/cantera/_cantera.pxd index e296b6560..13b77e10a 100644 --- a/interfaces/cython/cantera/_cantera.pxd +++ b/interfaces/cython/cantera/_cantera.pxd @@ -579,6 +579,8 @@ cdef extern from "cantera/zeroD/ReactorNet.h": double atol() void setMaxTimeStep(double) void setMaxErrTestFails(int) + void setMaxSteps(int) + int maxSteps() cbool verbose() void setVerbose(cbool) size_t neq() diff --git a/interfaces/cython/cantera/reactor.pyx b/interfaces/cython/cantera/reactor.pyx index 283983de5..db7730f1f 100644 --- a/interfaces/cython/cantera/reactor.pyx +++ b/interfaces/cython/cantera/reactor.pyx @@ -896,6 +896,16 @@ cdef class ReactorNet: def __set__(self, n): self.net.setMaxErrTestFails(n) + property max_steps: + """ + The maximum number of internal integration time-steps that CVODES + is allowed to take before reaching the next output time. + """ + def __set__(self, nsteps): + self.net.setMaxSteps(nsteps) + def __get__(self): + return self.net.maxSteps() + property rtol: """ The relative error tolerance used while integrating the reactor diff --git a/interfaces/cython/cantera/test/test_reactor.py b/interfaces/cython/cantera/test/test_reactor.py index cc2990924..11f759a17 100644 --- a/interfaces/cython/cantera/test/test_reactor.py +++ b/interfaces/cython/cantera/test/test_reactor.py @@ -140,6 +140,22 @@ class TestReactor(utilities.CanteraTest): #self.assertNear(self.net.time, tEnd) + def test_maxsteps(self): + self.make_reactors() + + # set the up a case where we can't take + # enough time-steps to reach the endtime + max_steps = 10 + max_step_size = 1e-07 + self.net.set_initial_time(0) + self.net.set_max_time_step(max_step_size) + self.net.max_steps = max_steps + with self.assertRaisesRegex( + ct.CanteraError, 'mxstep steps taken before reaching tout'): + self.net.advance(1e-04) + self.assertLessEqual(self.net.time, max_steps * max_step_size) + self.assertEqual(self.net.max_steps, max_steps) + def test_equalize_pressure(self): self.make_reactors(P1=101325, P2=300000) self.add_wall(K=0.1, A=1.0) diff --git a/src/numerics/CVodesIntegrator.cpp b/src/numerics/CVodesIntegrator.cpp index f3ff9809b..98b2acbf7 100644 --- a/src/numerics/CVodesIntegrator.cpp +++ b/src/numerics/CVodesIntegrator.cpp @@ -210,6 +210,11 @@ void CVodesIntegrator::setMaxSteps(int nmax) } } +int CVodesIntegrator::maxSteps() +{ + return m_maxsteps; +} + void CVodesIntegrator::setMaxErrTestFails(int n) { m_maxErrTestFails = n;