diff --git a/CHANGELOG.md b/CHANGELOG.md index 2b16f4c19f..3a893f0c2f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,7 @@ ### Fixed (Repair bugs, etc) ### Added (new features/APIs/variables/...) +- [[PR300]](https://github.com/lanl/singularity-eos/pull/300) Expose entropy functionality to Python API ### Changed (changing behavior/API/variables/...) @@ -37,13 +38,11 @@ Date: 11/28/2023 - [[PR308]](https://github.com/lanl/singularity-eos/pull/308) spack builds +fortran now compile via correct blocking out of interfaces via preprocessor ifdef ### Added (new features/APIs/variables/...) -- [[PR269]](https://github.com/lanl/singularity-eos/pull/269) Add SAP Polynomial EoS -- [[PR278]](https://github.com/lanl/singularity-eos/pull/278) Added EOSPAC option functionality in class constructor + - [[PR278]](https://github.com/lanl/singularity-eos/pull/278) Added a new function for returning the minimum energy as a function of density for an EOS (only EOSPAC at the moment) - [[PR278]](https://github.com/lanl/singularity-eos/pull/278) Added a new Fortran API for simple pressure and bulk moduli lookups - [[PR306]](https://github.com/lanl/singularity-eos/pull/306) Added generic Evaluate method - [[PR304]](https://github.com/lanl/singularity-eos/pull/304) added a Newton-Raphson root find for use with the Helmholtz EoS -- [[PR265]](https://github.com/lanl/singularity-eos/pull/265) Add missing UnitSystem modifier combinations to variant and EOSPAC - [[PR279]](https://github.com/lanl/singularity-eos/pull/279) added noble-abel EoS - [[PR274]](https://github.com/lanl/singularity-eos/pull/274) added a stiffened gas EoS - [[PR264]](https://github.com/lanl/singularity-eos/pull/274) added a Helmholtz EoS diff --git a/python/module.cpp b/python/module.cpp index 81db516a72..265081b53b 100644 --- a/python/module.cpp +++ b/python/module.cpp @@ -20,6 +20,7 @@ PYBIND11_MODULE(singularity_eos, m) { .def_readwrite("density", &EOSState::density) .def_readwrite("specific_internal_energy", &EOSState::specific_internal_energy) .def_readwrite("pressure", &EOSState::pressure) + .def_readwrite("entropy", &EOSState::entropy) .def_readwrite("temperature", &EOSState::temperature) .def_readwrite("specific_heat", &EOSState::specific_heat) .def_readwrite("bulk_modulus", &EOSState::bulk_modulus) diff --git a/python/module.hpp b/python/module.hpp index a4a3788a8f..65c8cb8703 100644 --- a/python/module.hpp +++ b/python/module.hpp @@ -99,6 +99,8 @@ void func####NoLambdaWithScratch(const T & self, py::array_t a, py::array_ EOS_VEC_FUNC_TMPL(TemperatureFromDensityInternalEnergy, rhos, sies, temperatures) EOS_VEC_FUNC_TMPL(InternalEnergyFromDensityTemperature, rhos, temperatures, sies) EOS_VEC_FUNC_TMPL(PressureFromDensityTemperature, rhos, temperatures, pressures) +EOS_VEC_FUNC_TMPL(EntropyFromDensityTemperature, rhos, temperatures, pressures) +EOS_VEC_FUNC_TMPL(EntropyFromDensityInternalEnergy, rhos, sies, pressures) EOS_VEC_FUNC_TMPL(PressureFromDensityInternalEnergy, rhos, sies, pressures) EOS_VEC_FUNC_TMPL(SpecificHeatFromDensityTemperature, rhos, temperatures, cvs) EOS_VEC_FUNC_TMPL(SpecificHeatFromDensityInternalEnergy, rhos, sies, cvs) @@ -111,6 +113,7 @@ struct EOSState { Real density; Real specific_internal_energy; Real pressure; + Real entropy; Real temperature; Real specific_heat; Real bulk_modulus; @@ -124,6 +127,7 @@ struct EOSState { density(std::numeric_limits::quiet_NaN()), specific_internal_energy(std::numeric_limits::quiet_NaN()), pressure(std::numeric_limits::quiet_NaN()), + entropy(std::numeric_limits::quiet_NaN()), temperature(std::numeric_limits::quiet_NaN()), specific_heat(std::numeric_limits::quiet_NaN()), bulk_modulus(std::numeric_limits::quiet_NaN()), @@ -139,6 +143,7 @@ struct EOSState { if(!std::isnan(density)) ss << "density: " << density << std::endl; if(!std::isnan(specific_internal_energy)) ss << "specific_internal_energy: " << specific_internal_energy << std::endl; if(!std::isnan(pressure)) ss << "pressure: " << pressure << std::endl; + if(!std::isnan(entropy)) ss << "entropy: " << entropy << std::endl; if(!std::isnan(temperature)) ss << "temperature: " << temperature << std::endl; if(!std::isnan(specific_heat)) ss << "specific_heat: " << specific_heat << std::endl; if(!std::isnan(bulk_modulus)) ss << "bulk_modulus: " << bulk_modulus << std::endl; @@ -160,6 +165,8 @@ struct VectorFunctions { .def("InternalEnergyFromDensityTemperature", &InternalEnergyFromDensityTemperature, py::arg("rhos"), py::arg("temperatures"), py::arg("sies"), py::arg("num"), py::arg("lmbdas")) .def("PressureFromDensityTemperature", &PressureFromDensityTemperature, py::arg("rhos"), py::arg("temperatures"), py::arg("pressures"), py::arg("num"), py::arg("lmbdas")) .def("PressureFromDensityInternalEnergy", &PressureFromDensityInternalEnergy, py::arg("rhos"), py::arg("sies"), py::arg("pressures"), py::arg("num"), py::arg("lmbdas")) + .def("EntropyFromDensityTemperature", &EntropyFromDensityTemperature, py::arg("rhos"), py::arg("temperatures"), py::arg("pressures"), py::arg("num"), py::arg("lmbdas")) + .def("EntropyFromDensityInternalEnergy", &EntropyFromDensityInternalEnergy, py::arg("rhos"), py::arg("sies"), py::arg("pressures"), py::arg("num"), py::arg("lmbdas")) .def("SpecificHeatFromDensityTemperature", &SpecificHeatFromDensityTemperature, py::arg("rhos"), py::arg("temperatures"), py::arg("cvs"), py::arg("num"), py::arg("lmbdas")) .def("SpecificHeatFromDensityInternalEnergy", &SpecificHeatFromDensityInternalEnergy, py::arg("rhos"), py::arg("sies"), py::arg("cvs"), py::arg("num"), py::arg("lmbdas")) .def("BulkModulusFromDensityTemperature", &BulkModulusFromDensityTemperature, py::arg("rhos"), py::arg("temperatures"), py::arg("bmods"), py::arg("num"), py::arg("lmbdas")) @@ -171,6 +178,8 @@ struct VectorFunctions { .def("InternalEnergyFromDensityTemperature", &InternalEnergyFromDensityTemperatureNoLambda, py::arg("rhos"), py::arg("temperatures"), py::arg("sies"), py::arg("num")) .def("PressureFromDensityTemperature", &PressureFromDensityTemperatureNoLambda, py::arg("rhos"), py::arg("temperatures"), py::arg("pressures"), py::arg("num")) .def("PressureFromDensityInternalEnergy", &PressureFromDensityInternalEnergyNoLambda, py::arg("rhos"), py::arg("sies"), py::arg("pressures"), py::arg("num")) + .def("EntropyFromDensityTemperature", &EntropyFromDensityTemperatureNoLambda, py::arg("rhos"), py::arg("temperatures"), py::arg("pressures"), py::arg("num")) + .def("EntropyFromDensityInternalEnergy", &EntropyFromDensityInternalEnergyNoLambda, py::arg("rhos"), py::arg("sies"), py::arg("pressures"), py::arg("num")) .def("SpecificHeatFromDensityTemperature", &SpecificHeatFromDensityTemperatureNoLambda, py::arg("rhos"), py::arg("temperatures"), py::arg("cvs"), py::arg("num")) .def("SpecificHeatFromDensityInternalEnergy", &SpecificHeatFromDensityInternalEnergyNoLambda, py::arg("rhos"), py::arg("sies"), py::arg("cvs"), py::arg("num")) .def("BulkModulusFromDensityTemperature", &BulkModulusFromDensityTemperatureNoLambda, py::arg("rhos"), py::arg("temperatures"), py::arg("bmods"), py::arg("num")) @@ -218,6 +227,8 @@ struct VectorFunctions { .def("InternalEnergyFromDensityTemperature", &InternalEnergyFromDensityTemperatureWithScratch, py::arg("rhos"), py::arg("temperatures"), py::arg("sies"), py::arg("scratch"), py::arg("num"), py::arg("lmbdas")) .def("PressureFromDensityTemperature", &PressureFromDensityTemperatureWithScratch, py::arg("rhos"), py::arg("temperatures"), py::arg("pressures"), py::arg("scratch"), py::arg("num"), py::arg("lmbdas")) .def("PressureFromDensityInternalEnergy", &PressureFromDensityInternalEnergyWithScratch, py::arg("rhos"), py::arg("sies"), py::arg("pressures"), py::arg("scratch"), py::arg("num"), py::arg("lmbdas")) + .def("EntropyFromDensityTemperature", &EntropyFromDensityTemperatureWithScratch, py::arg("rhos"), py::arg("temperatures"), py::arg("pressures"), py::arg("scratch"), py::arg("num"), py::arg("lmbdas")) + .def("EntropyFromDensityInternalEnergy", &EntropyFromDensityInternalEnergyWithScratch, py::arg("rhos"), py::arg("sies"), py::arg("pressures"), py::arg("scratch"), py::arg("num"), py::arg("lmbdas")) .def("SpecificHeatFromDensityTemperature", &SpecificHeatFromDensityTemperatureWithScratch, py::arg("rhos"), py::arg("temperatures"), py::arg("cvs"), py::arg("scratch"), py::arg("num"), py::arg("lmbdas")) .def("SpecificHeatFromDensityInternalEnergy", &SpecificHeatFromDensityInternalEnergyWithScratch, py::arg("rhos"), py::arg("sies"), py::arg("cvs"), py::arg("scratch"), py::arg("num"), py::arg("lmbdas")) .def("BulkModulusFromDensityTemperature", &BulkModulusFromDensityTemperatureWithScratch, py::arg("rhos"), py::arg("temperatures"), py::arg("bmods"), py::arg("scratch"), py::arg("num"), py::arg("lmbdas")) @@ -229,6 +240,8 @@ struct VectorFunctions { .def("InternalEnergyFromDensityTemperature", &InternalEnergyFromDensityTemperatureNoLambdaWithScratch, py::arg("rhos"), py::arg("temperatures"), py::arg("sies"), py::arg("scratch"), py::arg("num")) .def("PressureFromDensityTemperature", &PressureFromDensityTemperatureNoLambdaWithScratch, py::arg("rhos"), py::arg("temperatures"), py::arg("pressures"), py::arg("scratch"), py::arg("num")) .def("PressureFromDensityInternalEnergy", &PressureFromDensityInternalEnergyNoLambdaWithScratch, py::arg("rhos"), py::arg("sies"), py::arg("pressures"), py::arg("scratch"), py::arg("num")) + .def("EntropyFromDensityTemperature", &EntropyFromDensityTemperatureNoLambdaWithScratch, py::arg("rhos"), py::arg("temperatures"), py::arg("pressures"), py::arg("scratch"), py::arg("num")) + .def("EntropyFromDensityInternalEnergy", &EntropyFromDensityInternalEnergyNoLambdaWithScratch, py::arg("rhos"), py::arg("sies"), py::arg("pressures"), py::arg("scratch"), py::arg("num")) .def("SpecificHeatFromDensityTemperature", &SpecificHeatFromDensityTemperatureNoLambdaWithScratch, py::arg("rhos"), py::arg("temperatures"), py::arg("cvs"), py::arg("scratch"), py::arg("num")) .def("SpecificHeatFromDensityInternalEnergy", &SpecificHeatFromDensityInternalEnergyNoLambdaWithScratch, py::arg("rhos"), py::arg("sies"), py::arg("cvs"), py::arg("scratch"), py::arg("num")) .def("BulkModulusFromDensityTemperature", &BulkModulusFromDensityTemperatureNoLambdaWithScratch, py::arg("rhos"), py::arg("temperatures"), py::arg("bmods"), py::arg("scratch"), py::arg("num")) @@ -277,6 +290,8 @@ py::class_ eos_class(py::module_ & m, std::string name) { .def("InternalEnergyFromDensityTemperature", &two_params, py::arg("rho"), py::arg("temperature"), py::arg("lmbda")) .def("PressureFromDensityTemperature", &two_params, py::arg("rho"), py::arg("temperature"), py::arg("lmbda")) .def("PressureFromDensityInternalEnergy", &two_params, py::arg("rho"), py::arg("sie"), py::arg("lmbda")) + .def("EntropyFromDensityTemperature", &two_params, py::arg("rho"), py::arg("temperature"), py::arg("lmbda")) + .def("EntropyFromDensityInternalEnergy", &two_params, py::arg("rho"), py::arg("sie"), py::arg("lmbda")) .def("SpecificHeatFromDensityTemperature", &two_params, py::arg("rho"), py::arg("temperature"), py::arg("lmbda")) .def("SpecificHeatFromDensityInternalEnergy", &two_params, py::arg("rho"), py::arg("sie"), py::arg("lmbda")) .def("BulkModulusFromDensityTemperature", &two_params, py::arg("rho"), py::arg("temperature"), py::arg("lmbda")) diff --git a/test/python_bindings.py b/test/python_bindings.py index 5ae87f006d..d643bd3ea8 100644 --- a/test/python_bindings.py +++ b/test/python_bindings.py @@ -275,6 +275,7 @@ def setUp(self): # Gold standard values self.pressure_true = np.array((2.0, 8.0, 30.0)) self.temperature_true = np.array((1., 2., 3.)) + self.entropy_true = np.array((-13.516481508310815, -11.43703996663098, -11.242295889838465)) self.bulkmodulus_true = np.array((2.8, 11.2, 42.)) self.heatcapacity_true = np.array((Cv, Cv, Cv)) self.gruneisen_true = np.array((gm1, gm1, gm1)) @@ -282,6 +283,7 @@ def setUp(self): # Create arrays for the outputs self.temperature = np.zeros(self.num) self.pressure = np.zeros(self.num) + self.entropy = np.zeros(self.num) self.heatcapacity = np.zeros(self.num) self.bulkmodulus = np.zeros(self.num) self.gruneisen = np.zeros(self.num) @@ -296,6 +298,11 @@ def test_pressure(self): self.eos.PressureFromDensityInternalEnergy(self.density, self.energy, self.pressure, self.num) assert_allclose(self.pressure, self.pressure_true, rtol=1e-12) + def test_entropy(self): + """[Vector EOS][IdealGas][Energies and densities] A S(rho, e) lookup is performed""" + self.eos.EntropyFromDensityInternalEnergy(self.density, self.energy, self.entropy, self.num) + assert_allclose(self.entropy, self.entropy_true, rtol=1e-8) + def test_cv(self): """[Vector EOS][IdealGas][Energies and densities] A C_v(rho, e) lookup is performed""" self.eos.SpecificHeatFromDensityInternalEnergy(self.density, self.energy, self.heatcapacity, self.num) @@ -333,6 +340,7 @@ def setUp(self): # Gold standard values self.energy_true = np.array((250., 500., 750.)) self.pressure_true = np.array((100., 400., 1500.)) + self.entropy_true = np.array((6.0436335188299175, 8.123075060509752, 8.317819137302264)) self.bulkmodulus_true = np.array((140., 560., 2100.)) self.heatcapacity_true = np.array((Cv, Cv, Cv)) self.gruneisen_true = np.array((gm1, gm1, gm1)) @@ -340,6 +348,7 @@ def setUp(self): # Create arrays for the outputs self.energy = np.zeros(self.num) self.pressure = np.zeros(self.num) + self.entropy = np.zeros(self.num) self.heatcapacity = np.zeros(self.num) self.bulkmodulus = np.zeros(self.num) self.gruneisen = np.zeros(self.num) @@ -354,6 +363,11 @@ def test_pressure(self): self.eos.PressureFromDensityTemperature(self.density, self.temperature, self.pressure, self.num) assert_allclose(self.pressure, self.pressure_true, rtol=1e-12) + def test_entropy(self): + """[Vector EOS][IdealGas][Densities and temperatures] A S(rho, T) lookup is performed""" + self.eos.EntropyFromDensityTemperature(self.density, self.temperature, self.entropy, self.num) + assert_allclose(self.entropy, self.entropy_true, rtol=1e-12) + def test_cv(self): """[Vector EOS][IdealGas][Densities and temperatures] A C_v(rho, T) lookup is performed""" self.eos.SpecificHeatFromDensityTemperature(self.density, self.temperature, self.heatcapacity, self.num)