feat(MaskedComposition): added MaskedComposition to libcomposition
MaskedComposition is a generally useful decorator, therefore instead of forcing callers to impliment it on their own, we have implimented it as part of libcomposition
This commit is contained in:
2
Doxyfile
2
Doxyfile
@@ -48,7 +48,7 @@ PROJECT_NAME = fourdst::libcomposition
|
||||
# could be handy for archiving the generated documentation or if some version
|
||||
# control system is used.
|
||||
|
||||
PROJECT_NUMBER = v2.0.4
|
||||
PROJECT_NUMBER = v2.0.6
|
||||
|
||||
# Using the PROJECT_BRIEF tag one can provide an optional one line description
|
||||
# for a project that appears at the top of each page and should give viewers a
|
||||
|
||||
@@ -18,7 +18,7 @@
|
||||
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||
#
|
||||
# *********************************************************************** #
|
||||
project('libcomposition', 'cpp', version: 'v2.0.4', default_options: ['cpp_std=c++23'], meson_version: '>=1.5.0')
|
||||
project('libcomposition', 'cpp', version: 'v2.0.6', default_options: ['cpp_std=c++23'], meson_version: '>=1.5.0')
|
||||
|
||||
# Add default visibility for all C++ targets
|
||||
add_project_arguments('-fvisibility=default', language: 'cpp')
|
||||
|
||||
@@ -4,6 +4,7 @@
|
||||
|
||||
#include <string>
|
||||
#include <unordered_map>
|
||||
#include <map>
|
||||
#include <set>
|
||||
#include <vector>
|
||||
|
||||
@@ -180,46 +181,4 @@ namespace fourdst::composition {
|
||||
};
|
||||
|
||||
// ReSharper disable once CppClassCanBeFinal
|
||||
class CompositionDecorator : public CompositionAbstract {
|
||||
public:
|
||||
explicit CompositionDecorator(std::unique_ptr<CompositionAbstract> decorator) : m_base_composition(std::move(decorator)) {};
|
||||
[[nodiscard]] bool contains(const atomic::Species &species) const noexcept override { return m_base_composition->contains(species); };
|
||||
[[nodiscard]] bool contains(const std::string& symbol) const override { return m_base_composition->contains(symbol); };
|
||||
[[nodiscard]] size_t size() const noexcept override { return m_base_composition->size(); };
|
||||
[[nodiscard]] std::set<std::string> getRegisteredSymbols() const noexcept override { return m_base_composition->getRegisteredSymbols(); };
|
||||
[[nodiscard]] const std::set<atomic::Species> &getRegisteredSpecies() const noexcept override { return m_base_composition->getRegisteredSpecies(); };
|
||||
[[nodiscard]] std::unordered_map<atomic::Species, double> getMassFraction() const noexcept override { return m_base_composition->getMassFraction(); };
|
||||
[[nodiscard]] std::unordered_map<atomic::Species, double> getNumberFraction() const noexcept override { return m_base_composition->getNumberFraction(); };
|
||||
[[nodiscard]] double getMassFraction(const std::string& symbol) const override { return m_base_composition->getMassFraction(symbol); };
|
||||
[[nodiscard]] double getMassFraction(const atomic::Species& species) const override { return m_base_composition->getMassFraction(species); };
|
||||
[[nodiscard]] double getNumberFraction(const std::string& symbol) const override { return m_base_composition->getNumberFraction(symbol); };
|
||||
[[nodiscard]] double getNumberFraction(const atomic::Species& species) const override { return m_base_composition->getNumberFraction(species); };
|
||||
[[nodiscard]] double getMolarAbundance(const std::string& symbol) const override { return m_base_composition->getMolarAbundance(symbol); };
|
||||
[[nodiscard]] double getMolarAbundance(const atomic::Species& species) const override { return m_base_composition->getMolarAbundance(species); };
|
||||
[[nodiscard]] double getMeanParticleMass() const noexcept override { return m_base_composition->getMeanParticleMass(); };
|
||||
[[nodiscard]] double getElectronAbundance() const noexcept override { return m_base_composition->getElectronAbundance(); };
|
||||
[[nodiscard]] std::vector<double> getMassFractionVector() const noexcept override { return m_base_composition->getMassFractionVector(); };
|
||||
[[nodiscard]] std::vector<double> getNumberFractionVector() const noexcept override { return m_base_composition->getNumberFractionVector(); };
|
||||
[[nodiscard]] std::vector<double> getMolarAbundanceVector() const noexcept override { return m_base_composition->getMolarAbundanceVector(); };
|
||||
[[nodiscard]] size_t getSpeciesIndex(const std::string& symbol) const override { return m_base_composition->getSpeciesIndex(symbol); };
|
||||
[[nodiscard]] size_t getSpeciesIndex(const atomic::Species& species) const override { return m_base_composition->getSpeciesIndex(species); };
|
||||
[[nodiscard]] atomic::Species getSpeciesAtIndex(const size_t index) const override { return m_base_composition->getSpeciesAtIndex(index); };
|
||||
[[nodiscard]] std::unique_ptr<CompositionAbstract> clone() const override {
|
||||
return std::make_unique<CompositionDecorator>(m_base_composition->clone());
|
||||
}
|
||||
[[nodiscard]] std::map<atomic::Species, double>::iterator begin() override {
|
||||
return m_base_composition->begin();
|
||||
}
|
||||
[[nodiscard]] std::map<atomic::Species, double>::iterator end() override {
|
||||
return m_base_composition->end();
|
||||
}
|
||||
[[nodiscard]] std::map<atomic::Species, double>::const_iterator begin() const override {
|
||||
return std::as_const(*m_base_composition).begin();
|
||||
}
|
||||
[[nodiscard]] std::map<atomic::Species, double>::const_iterator end() const override {
|
||||
return std::as_const(*m_base_composition).end();
|
||||
}
|
||||
private:
|
||||
std::unique_ptr<CompositionAbstract> m_base_composition;
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,48 @@
|
||||
#pragma once
|
||||
|
||||
#include "fourdst/atomic/atomicSpecies.h"
|
||||
|
||||
#include "fourdst/composition/composition_abstract.h"
|
||||
|
||||
#include <utility>
|
||||
#include <set>
|
||||
#include <unordered_map>
|
||||
#include <map>
|
||||
#include <vector>
|
||||
|
||||
namespace fourdst::composition {
|
||||
|
||||
class CompositionDecorator: public CompositionAbstract {
|
||||
public:
|
||||
explicit CompositionDecorator(std::unique_ptr<CompositionAbstract> decorator) : m_base_composition(std::move(decorator)) {};
|
||||
[[nodiscard]] bool contains(const atomic::Species &species) const noexcept override { return m_base_composition->contains(species); };
|
||||
[[nodiscard]] bool contains(const std::string& symbol) const override { return m_base_composition->contains(symbol); };
|
||||
[[nodiscard]] size_t size() const noexcept override { return m_base_composition->size(); };
|
||||
[[nodiscard]] std::set<std::string> getRegisteredSymbols() const noexcept override { return m_base_composition->getRegisteredSymbols(); };
|
||||
[[nodiscard]] const std::set<atomic::Species> &getRegisteredSpecies() const noexcept override { return m_base_composition->getRegisteredSpecies(); };
|
||||
[[nodiscard]] std::unordered_map<atomic::Species, double> getMassFraction() const noexcept override { return m_base_composition->getMassFraction(); };
|
||||
[[nodiscard]] std::unordered_map<atomic::Species, double> getNumberFraction() const noexcept override { return m_base_composition->getNumberFraction(); };
|
||||
[[nodiscard]] double getMassFraction(const std::string& symbol) const override { return m_base_composition->getMassFraction(symbol); };
|
||||
[[nodiscard]] double getMassFraction(const atomic::Species& species) const override { return m_base_composition->getMassFraction(species); };
|
||||
[[nodiscard]] double getNumberFraction(const std::string& symbol) const override { return m_base_composition->getNumberFraction(symbol); };
|
||||
[[nodiscard]] double getNumberFraction(const atomic::Species& species) const override { return m_base_composition->getNumberFraction(species); };
|
||||
[[nodiscard]] double getMolarAbundance(const std::string& symbol) const override { return m_base_composition->getMolarAbundance(symbol); };
|
||||
[[nodiscard]] double getMolarAbundance(const atomic::Species& species) const override { return m_base_composition->getMolarAbundance(species); };
|
||||
[[nodiscard]] double getMeanParticleMass() const noexcept override { return m_base_composition->getMeanParticleMass(); };
|
||||
[[nodiscard]] double getElectronAbundance() const noexcept override { return m_base_composition->getElectronAbundance(); };
|
||||
[[nodiscard]] std::vector<double> getMassFractionVector() const noexcept override { return m_base_composition->getMassFractionVector(); };
|
||||
[[nodiscard]] std::vector<double> getNumberFractionVector() const noexcept override { return m_base_composition->getNumberFractionVector(); };
|
||||
[[nodiscard]] std::vector<double> getMolarAbundanceVector() const noexcept override { return m_base_composition->getMolarAbundanceVector(); };
|
||||
[[nodiscard]] size_t getSpeciesIndex(const std::string& symbol) const override { return m_base_composition->getSpeciesIndex(symbol); };
|
||||
[[nodiscard]] size_t getSpeciesIndex(const atomic::Species& species) const override { return m_base_composition->getSpeciesIndex(species); };
|
||||
[[nodiscard]] atomic::Species getSpeciesAtIndex(const size_t index) const override { return m_base_composition->getSpeciesAtIndex(index); }
|
||||
|
||||
[[nodiscard]] std::map<atomic::Species, double>::iterator begin() override { return m_base_composition->begin(); };
|
||||
[[nodiscard]] std::map<atomic::Species, double>::iterator end() override { return m_base_composition->end(); };
|
||||
|
||||
[[nodiscard]] std::map<atomic::Species, double>::const_iterator begin() const override { return std::as_const(*m_base_composition).begin(); };
|
||||
[[nodiscard]] std::map<atomic::Species, double>::const_iterator end() const override { return std::as_const(*m_base_composition).end(); };
|
||||
protected:
|
||||
std::unique_ptr<CompositionAbstract> m_base_composition;
|
||||
};
|
||||
}
|
||||
@@ -0,0 +1,65 @@
|
||||
#pragma once
|
||||
|
||||
#include "fourdst/composition/decorators/composition_decorator_abstract.h"
|
||||
#include "fourdst/composition/exceptions/exceptions_composition.h"
|
||||
#include "fourdst/atomic/atomicSpecies.h"
|
||||
|
||||
namespace fourdst::composition {
|
||||
class MaskedComposition final : public CompositionDecorator {
|
||||
public:
|
||||
MaskedComposition(
|
||||
const CompositionAbstract& baseComposition,
|
||||
const std::set<atomic::Species>& activeSpecies
|
||||
);
|
||||
|
||||
[[nodiscard]] bool contains(const atomic::Species &species) const noexcept override;
|
||||
|
||||
[[nodiscard]] bool contains(const std::string &symbol) const override;
|
||||
|
||||
[[nodiscard]] const std::set<atomic::Species>& getRegisteredSpecies() const noexcept override;
|
||||
|
||||
[[nodiscard]] std::set<std::string> getRegisteredSymbols() const noexcept override;
|
||||
|
||||
[[nodiscard]] size_t size() const noexcept override;
|
||||
|
||||
[[nodiscard]] std::unordered_map<atomic::Species, double> getMassFraction() const noexcept override;
|
||||
|
||||
[[nodiscard]] std::unordered_map<atomic::Species, double> getNumberFraction() const noexcept override;
|
||||
|
||||
[[nodiscard]] double getMassFraction(const std::string &symbol) const override;
|
||||
[[nodiscard]] double getMassFraction(const atomic::Species &species) const override;
|
||||
[[nodiscard]] double getNumberFraction(const std::string &symbol) const override;
|
||||
[[nodiscard]] double getNumberFraction(const atomic::Species &species) const override;
|
||||
[[nodiscard]] double getMolarAbundance(const std::string &symbol) const override;
|
||||
[[nodiscard]] double getMolarAbundance(const atomic::Species &species) const override;
|
||||
[[nodiscard]] double getMeanParticleMass() const noexcept override;
|
||||
|
||||
[[nodiscard]] double getElectronAbundance() const noexcept override;
|
||||
|
||||
[[nodiscard]] std::vector<double> getMassFractionVector() const noexcept override;
|
||||
|
||||
[[nodiscard]] std::vector<double> getNumberFractionVector() const noexcept override;
|
||||
|
||||
[[nodiscard]] std::vector<double> getMolarAbundanceVector() const noexcept override;
|
||||
|
||||
[[nodiscard]] size_t getSpeciesIndex(const std::string &symbol) const override;
|
||||
|
||||
[[nodiscard]] size_t getSpeciesIndex(const atomic::Species &species) const override;
|
||||
|
||||
[[nodiscard]] atomic::Species getSpeciesAtIndex(size_t index) const override;
|
||||
|
||||
[[nodiscard]] std::unique_ptr<CompositionAbstract> clone() const override;
|
||||
|
||||
[[nodiscard]] std::map<atomic::Species, double>::iterator begin() override;
|
||||
|
||||
[[nodiscard]] std::map<atomic::Species, double>::iterator end() override;
|
||||
|
||||
[[nodiscard]] std::map<atomic::Species, double>::const_iterator begin() const override;
|
||||
|
||||
[[nodiscard]] std::map<atomic::Species, double>::const_iterator end() const override;
|
||||
private:
|
||||
std::set<atomic::Species> m_activeSpecies;
|
||||
std::map<atomic::Species, double> m_masked_composition;
|
||||
};
|
||||
|
||||
}
|
||||
216
src/composition/lib/decorators/composition_masked.cpp
Normal file
216
src/composition/lib/decorators/composition_masked.cpp
Normal file
@@ -0,0 +1,216 @@
|
||||
#include "fourdst/composition/decorators/composition_masked.h"
|
||||
|
||||
#include "fourdst/atomic/species.h"
|
||||
|
||||
namespace fourdst::composition {
|
||||
MaskedComposition::MaskedComposition(
|
||||
const CompositionAbstract& baseComposition,
|
||||
const std::set<atomic::Species>& activeSpecies
|
||||
) :
|
||||
CompositionDecorator(baseComposition.clone()),
|
||||
m_activeSpecies(activeSpecies) {
|
||||
for (const auto& species : m_activeSpecies) {
|
||||
if (CompositionDecorator::contains(species)) {
|
||||
m_masked_composition.emplace(species, CompositionDecorator::getMolarAbundance(species));
|
||||
} else {
|
||||
m_masked_composition.emplace(species, 0.0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool MaskedComposition::contains(const atomic::Species &species) const noexcept{
|
||||
if (m_activeSpecies.contains(species)) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool MaskedComposition::contains(const std::string &symbol) const {
|
||||
if (!atomic::species.contains(symbol)) {
|
||||
throw exceptions::UnknownSymbolError("Cannot find species '" + symbol + "' in base composition");
|
||||
}
|
||||
const atomic::Species& species = atomic::species.at(symbol);
|
||||
if (m_activeSpecies.contains(species)) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
const std::set<atomic::Species>& MaskedComposition::getRegisteredSpecies() const noexcept {
|
||||
return m_activeSpecies;
|
||||
}
|
||||
|
||||
std::set<std::string> MaskedComposition::getRegisteredSymbols() const noexcept {
|
||||
std::set<std::string> symbols;
|
||||
for (const auto& species : m_activeSpecies) {
|
||||
symbols.insert(std::string(species.name()));
|
||||
}
|
||||
return symbols;
|
||||
}
|
||||
|
||||
size_t MaskedComposition::size() const noexcept {
|
||||
return m_activeSpecies.size();
|
||||
}
|
||||
|
||||
std::unordered_map<atomic::Species, double> MaskedComposition::getMassFraction() const noexcept {
|
||||
std::unordered_map<atomic::Species, double> massFractions;
|
||||
for (const auto& species : m_activeSpecies) {
|
||||
if (CompositionDecorator::contains(species)) {
|
||||
massFractions[species] = CompositionDecorator::getMassFraction(species);
|
||||
} else {
|
||||
massFractions[species] = 0.0;
|
||||
}
|
||||
}
|
||||
return massFractions;
|
||||
}
|
||||
|
||||
std::unordered_map<atomic::Species, double> MaskedComposition::getNumberFraction() const noexcept {
|
||||
std::unordered_map<atomic::Species, double> numberFractions;
|
||||
for (const auto& species : m_activeSpecies) {
|
||||
if (CompositionDecorator::contains(species)) {
|
||||
numberFractions[species] = CompositionDecorator::getNumberFraction(species);
|
||||
} else {
|
||||
numberFractions[species] = 0.0;
|
||||
}
|
||||
}
|
||||
return numberFractions;
|
||||
}
|
||||
|
||||
double MaskedComposition::getMassFraction(const std::string &symbol) const {
|
||||
if (!contains(symbol)) {
|
||||
throw exceptions::UnregisteredSymbolError("Species '" + symbol + "' is not part of the active species in the MaskedComposition.");
|
||||
}
|
||||
if (CompositionDecorator::contains(symbol)) {
|
||||
return CompositionDecorator::getMassFraction(symbol);
|
||||
} return 0.0;
|
||||
}
|
||||
double MaskedComposition::getMassFraction(const atomic::Species &species) const {
|
||||
if (!contains(species)) {
|
||||
throw exceptions::UnregisteredSymbolError("Species '" + std::string(species.name()) + "' is not part of the active species in the MaskedComposition.");
|
||||
}
|
||||
if (CompositionDecorator::contains(species)) {
|
||||
return CompositionDecorator::getMassFraction(species);
|
||||
} return 0.0;
|
||||
}
|
||||
double MaskedComposition::getNumberFraction(const std::string &symbol) const {
|
||||
if (!contains(symbol)) {
|
||||
throw exceptions::UnregisteredSymbolError("Species '" + symbol + "' is not part of the active species in the MaskedComposition.");
|
||||
}
|
||||
if (CompositionDecorator::contains(symbol)) {
|
||||
return CompositionDecorator::getNumberFraction(symbol);
|
||||
} return 0.0;
|
||||
}
|
||||
double MaskedComposition::getNumberFraction(const atomic::Species &species) const {
|
||||
if (!contains(species)) {
|
||||
throw exceptions::UnregisteredSymbolError("Species '" + std::string(species.name()) + "' is not part of the active species in the MaskedComposition.");
|
||||
}
|
||||
if (CompositionDecorator::contains(species)) {
|
||||
return CompositionDecorator::getNumberFraction(species);
|
||||
} return 0.0;
|
||||
}
|
||||
double MaskedComposition::getMolarAbundance(const std::string &symbol) const {
|
||||
if (!contains(symbol)) {
|
||||
throw exceptions::UnregisteredSymbolError("Species '" + symbol + "' is not part of the active species in the MaskedComposition.");
|
||||
}
|
||||
if (CompositionDecorator::contains(symbol)) {
|
||||
return CompositionDecorator::getMolarAbundance(symbol);
|
||||
} return 0.0;
|
||||
}
|
||||
double MaskedComposition::getMolarAbundance(const atomic::Species &species) const {
|
||||
if (!contains(species)) {
|
||||
throw exceptions::UnregisteredSymbolError("Species '" + std::string(species.name()) + "' is not part of the active species in the MaskedComposition.");
|
||||
}
|
||||
if (CompositionDecorator::contains(species)) {
|
||||
return CompositionDecorator::getMolarAbundance(species);
|
||||
} return 0.0;
|
||||
}
|
||||
double MaskedComposition::getMeanParticleMass() const noexcept {
|
||||
double meanParticleMass = 0.0;
|
||||
for (const auto& species : m_activeSpecies) {
|
||||
if (CompositionDecorator::contains(species)) {
|
||||
const double numberFraction = CompositionDecorator::getNumberFraction(species);
|
||||
const double atomicMass = species.mass();
|
||||
meanParticleMass += numberFraction * atomicMass;
|
||||
}
|
||||
}
|
||||
return meanParticleMass;
|
||||
}
|
||||
|
||||
double MaskedComposition::getElectronAbundance() const noexcept {
|
||||
double Ye = 0.0;
|
||||
for (const auto& species : m_activeSpecies) {
|
||||
if (CompositionDecorator::contains(species)) {
|
||||
Ye += CompositionDecorator::getMolarAbundance(species) * species.z();
|
||||
}
|
||||
}
|
||||
return Ye;
|
||||
}
|
||||
|
||||
std::vector<double> MaskedComposition::getMassFractionVector() const noexcept {
|
||||
std::vector<double> massFractions;
|
||||
massFractions.reserve(m_activeSpecies.size());
|
||||
for (const auto& species : m_activeSpecies) {
|
||||
massFractions.push_back(getMassFraction(species));
|
||||
}
|
||||
return massFractions;
|
||||
}
|
||||
|
||||
std::vector<double> MaskedComposition::getNumberFractionVector() const noexcept {
|
||||
std::vector<double> numberFractions;
|
||||
numberFractions.reserve(m_activeSpecies.size());
|
||||
for (const auto& species : m_activeSpecies) {
|
||||
numberFractions.push_back(getNumberFraction(species));
|
||||
}
|
||||
return numberFractions;
|
||||
}
|
||||
|
||||
std::vector<double> MaskedComposition::getMolarAbundanceVector() const noexcept {
|
||||
std::vector<double> molarAbundances;
|
||||
molarAbundances.reserve(m_activeSpecies.size());
|
||||
for (const auto& species : m_activeSpecies) {
|
||||
molarAbundances.push_back(getMolarAbundance(species));
|
||||
}
|
||||
return molarAbundances;
|
||||
}
|
||||
|
||||
size_t MaskedComposition::getSpeciesIndex(const std::string &symbol) const {
|
||||
if (!contains(symbol)) {
|
||||
throw exceptions::UnregisteredSymbolError("Species '" + symbol + "' is not part of the active species in the MaskedComposition.");
|
||||
}
|
||||
return std::distance(m_activeSpecies.begin(), m_activeSpecies.find(atomic::species.at(symbol)));
|
||||
}
|
||||
|
||||
size_t MaskedComposition::getSpeciesIndex(const atomic::Species &species) const {
|
||||
return std::distance(m_activeSpecies.begin(), m_activeSpecies.find(species));
|
||||
}
|
||||
|
||||
atomic::Species MaskedComposition::getSpeciesAtIndex(const size_t index) const {
|
||||
if (index >= m_activeSpecies.size()) {
|
||||
throw std::out_of_range("Index " + std::to_string(index) + " is out of bounds for active species of size " + std::to_string(m_activeSpecies.size()) + ".");
|
||||
}
|
||||
auto it = m_activeSpecies.begin();
|
||||
std::advance(it, index);
|
||||
return *it;
|
||||
}
|
||||
|
||||
std::unique_ptr<CompositionAbstract> MaskedComposition::clone() const {
|
||||
return std::make_unique<MaskedComposition>(*m_base_composition, m_activeSpecies);
|
||||
}
|
||||
|
||||
std::map<atomic::Species, double>::iterator MaskedComposition::begin() {
|
||||
return m_masked_composition.begin();
|
||||
}
|
||||
|
||||
std::map<atomic::Species, double>::iterator MaskedComposition::end() {
|
||||
return m_masked_composition.end();
|
||||
}
|
||||
|
||||
std::map<atomic::Species, double>::const_iterator MaskedComposition::begin() const {
|
||||
return m_masked_composition.cbegin();
|
||||
}
|
||||
|
||||
std::map<atomic::Species, double>::const_iterator MaskedComposition::end() const {
|
||||
return m_masked_composition.cend();
|
||||
}
|
||||
};
|
||||
@@ -22,6 +22,7 @@ message('✅ libcomposition species_weight dependency declared')
|
||||
composition_sources = files(
|
||||
'lib/composition.cpp',
|
||||
'lib/utils.cpp',
|
||||
'lib/decorators/composition_masked.cpp',
|
||||
)
|
||||
|
||||
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
#include "fourdst/composition/composition.h"
|
||||
#include "fourdst/composition/exceptions/exceptions_composition.h"
|
||||
#include "fourdst/composition/utils.h"
|
||||
#include "fourdst/composition/composition_abstract.h"
|
||||
#include "fourdst/composition/decorators/composition_masked.h"
|
||||
|
||||
#include "fourdst/config/config.h"
|
||||
|
||||
@@ -236,41 +236,18 @@ TEST_F(compositionTest, buildFromMassFractions) {
|
||||
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* @brief Tests inheritance from CompositionAbstract and overriding a getter.
|
||||
* @details This test defines a derived class that overrides getMolarAbundance,
|
||||
* and verifies that the override works and other getters are inherited.
|
||||
* @par What this test proves:
|
||||
* - Derived classes can override getters.
|
||||
* - All CompositionAbstract children have the standard getter interface.
|
||||
*/
|
||||
TEST_F(compositionTest, abstractBase) {
|
||||
class UnrestrictedComposition : public fourdst::composition::CompositionDecorator {
|
||||
public:
|
||||
UnrestrictedComposition(std::unique_ptr<CompositionAbstract> base, const fourdst::atomic::Species& species):
|
||||
CompositionDecorator(std::move(base)),
|
||||
m_species(species)
|
||||
{}
|
||||
|
||||
double getMolarAbundance(const fourdst::atomic::Species &species) const override {
|
||||
if (species == m_species) {
|
||||
return 1.0;
|
||||
}
|
||||
return CompositionDecorator::getMolarAbundance(species);
|
||||
}
|
||||
private:
|
||||
fourdst::atomic::Species m_species;
|
||||
};
|
||||
|
||||
TEST_F(compositionTest, decorators) {
|
||||
fourdst::composition::Composition comp;
|
||||
comp.registerSymbol("H-1"); comp.registerSymbol("He-4"); comp.registerSymbol("O-16");
|
||||
comp.setMolarAbundance("H-1", 0.6); comp.setMolarAbundance("He-4", 0.6);
|
||||
const fourdst::composition::MaskedComposition mComp(comp, {fourdst::atomic::H_1, fourdst::atomic::He_4});
|
||||
|
||||
ASSERT_DOUBLE_EQ(mComp.getMolarAbundance(fourdst::atomic::H_1), 0.6);
|
||||
ASSERT_DOUBLE_EQ(mComp.getMolarAbundance("He-4"), 0.6);
|
||||
ASSERT_FALSE(mComp.contains("O-16"));
|
||||
|
||||
comp.setMolarAbundance("H-1", 1.0);
|
||||
ASSERT_NE(mComp.getMolarAbundance(fourdst::atomic::H_1), 1.0);
|
||||
|
||||
const UnrestrictedComposition uComp(std::make_unique<fourdst::composition::Composition>(comp), fourdst::atomic::H_1);
|
||||
|
||||
ASSERT_DOUBLE_EQ(uComp.getMolarAbundance(fourdst::atomic::H_1), 1.0);
|
||||
ASSERT_DOUBLE_EQ(uComp.getMassFraction("He-4"), comp.getMassFraction("He-4"));
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user