From 641bef6220422c61b23570bdeb4846b4285d921f Mon Sep 17 00:00:00 2001 From: Ingmar Schoegl Date: Sat, 1 Jul 2023 07:08:10 -0600 Subject: [PATCH] [Python] Rename TabulatedFunction to Tabulated1 --- doc/sphinx/cython/zerodim.rst | 2 +- interfaces/cython/cantera/func1.pyx | 59 +++++++++++++++++++++++++---- test/python/test_func1.py | 18 ++++----- 3 files changed, 62 insertions(+), 17 deletions(-) diff --git a/doc/sphinx/cython/zerodim.rst b/doc/sphinx/cython/zerodim.rst index 48e2cac000..cb476520e5 100644 --- a/doc/sphinx/cython/zerodim.rst +++ b/doc/sphinx/cython/zerodim.rst @@ -13,7 +13,7 @@ Defining Functions .. autoclass:: Func1 -.. autoclass:: TabulatedFunction +.. autoclass:: Tabulated1 Base Classes ------------ diff --git a/interfaces/cython/cantera/func1.pyx b/interfaces/cython/cantera/func1.pyx index a66037ada9..9d8be9c5eb 100644 --- a/interfaces/cython/cantera/func1.pyx +++ b/interfaces/cython/cantera/func1.pyx @@ -4,6 +4,7 @@ import sys cimport numpy as np import numpy as np +import warnings from ._utils cimport * @@ -180,7 +181,48 @@ cdef class Func1: raise NotImplementedError(msg) -cdef class TabulatedFunction(Func1): +cdef class Tabulated1(Func1): + """ + A `Tabulated1` object representing a tabulated function is defined by + sample points and corresponding function values. Inputs are specified by + two iterable objects containing sample point location and function values. + Between sample points, values are evaluated based on the optional argument + ``method``; options are ``'linear'`` (linear interpolation, default) or + ``'previous'`` (nearest previous value). Outside the sample interval, the + value at the closest end point is returned. + + Examples for `Tabulated1` objects are:: + + >>> t1 = Tabulated1([0, 1, 2], [2, 1, 0]) + >>> [t1(v) for v in [-0.5, 0, 0.5, 1.5, 2, 2.5]] + [2.0, 2.0, 1.5, 0.5, 0.0, 0.0] + + >>> t2 = Tabulated1(np.array([0, 1, 2]), np.array([2, 1, 0])) + >>> [t2(v) for v in [-0.5, 0, 0.5, 1.5, 2, 2.5]] + [2.0, 2.0, 1.5, 0.5, 0.0, 0.0] + + The optional ``method`` keyword argument changes the type of interpolation + from the ``'linear'`` default to ``'previous'``:: + + >>> t3 = Tabulated1([0, 1, 2], [2, 1, 0], method='previous') + >>> [t3(v) for v in [-0.5, 0, 0.5, 1.5, 2, 2.5]] + [2.0, 2.0, 2.0, 1.0, 0.0, 0.0] + + .. versionadded:: 3.0 + """ + + def __init__(self, time, fval, method='linear'): + cdef vector[double] arr + for v in time: + arr.push_back(v) + for v in fval: + arr.push_back(v) + cdef string cxx_string = stringify(f"tabulated-{method}") + self._func = CxxNewFunc1(cxx_string, arr) + self.func = self._func.get() + + +cdef class TabulatedFunction(Tabulated1): """ A `TabulatedFunction` object representing a tabulated function is defined by sample points and corresponding function values. Inputs are specified by @@ -206,10 +248,13 @@ cdef class TabulatedFunction(Func1): >>> t3 = TabulatedFunction([0, 1, 2], [2, 1, 0], method='previous') >>> [t3(v) for v in [-0.5, 0, 0.5, 1.5, 2, 2.5]] [2.0, 2.0, 2.0, 1.0, 0.0, 0.0] - """ - def __init__(self, time, fval, method='linear'): - arr = np.hstack([np.array(time), np.array(fval)]) - cdef Func1 func = Func1.cxx_functor(f"tabulated-{method}", arr) - self._func = func._func - self.func = self._func.get() + .. deprecated:: 3.0 + + To be removed after Cantera 3.0. Renamed to `Tabulated1`. + """ + def __init__(self, *args, **kwargs): + warnings.warn( + "TabulatedFunction: To be removed after Cantera 3.0. " + "Renamed to 'Tabulated1'.", DeprecationWarning) + super().__init__(*args, **kwargs) diff --git a/test/python/test_func1.py b/test/python/test_func1.py index 4d44dd9e4e..b94211bcff 100644 --- a/test/python/test_func1.py +++ b/test/python/test_func1.py @@ -127,7 +127,7 @@ def test_tabulated1(self): arr = np.array([[0, 2], [1, 1], [2, 0]]) time = arr[:, 0] fval = arr[:, 1] - fcn = ct.TabulatedFunction(time, fval) + fcn = ct.Tabulated1(time, fval) assert fcn.type == "tabulated-linear" for t, f in zip(time, fval): self.assertNear(f, fcn(t)) @@ -135,7 +135,7 @@ def test_tabulated1(self): def test_tabulated2(self): time = [0, 1, 2] fval = [2, 1, 0] - fcn = ct.TabulatedFunction(time, fval) + fcn = ct.Tabulated1(time, fval) assert fcn.type == "tabulated-linear" for t, f in zip(time, fval): self.assertNear(f, fcn(t)) @@ -143,14 +143,14 @@ def test_tabulated2(self): def test_tabulated3(self): time = 0, 1, 2, fval = 2, 1, 0, - fcn = ct.TabulatedFunction(time, fval) + fcn = ct.Tabulated1(time, fval) self.assertNear(fcn(-1), fval[0]) self.assertNear(fcn(3), fval[-1]) def test_tabulated4(self): time = np.array([0, 1, 2]) fval = np.array([2, 1, 0]) - fcn = ct.TabulatedFunction(time, fval) + fcn = ct.Tabulated1(time, fval) tt = .5*(time[1:] + time[:-1]) ff = .5*(fval[1:] + fval[:-1]) for t, f in zip(tt, ff): @@ -159,17 +159,17 @@ def test_tabulated4(self): def test_tabulated5(self): time = [0, 1, 2] fval = [2, 1, 0] - fcn = ct.TabulatedFunction(time, fval, method='previous') + fcn = ct.Tabulated1(time, fval, method='previous') assert fcn.type == "tabulated-previous" val = np.array([fcn(v) for v in [-0.5, 0, 0.5, 1.5, 2, 2.5]]) self.assertArrayNear(val, np.array([2.0, 2.0, 2.0, 1.0, 0.0, 0.0])) def test_tabulated_failures(self): with pytest.raises(ct.CanteraError, match="even number of entries"): - ct.TabulatedFunction(range(2), range(3)) + ct.Tabulated1(range(2), range(3)) with pytest.raises(ct.CanteraError, match="at least 4 entries"): - ct.TabulatedFunction([], []) + ct.Tabulated1([], []) with pytest.raises(ct.CanteraError, match="monotonically"): - ct.TabulatedFunction((0, 1, 0.5, 2), (2, 1, 1, 0)) + ct.Tabulated1((0, 1, 0.5, 2), (2, 1, 1, 0)) with pytest.raises(ct.CanteraError, match="No such type"): - ct.TabulatedFunction((0, 1, 1, 2), (2, 1, 1, 0), method='spam') + ct.Tabulated1((0, 1, 1, 2), (2, 1, 1, 0), method='spam')