Loading src/physics/Detrapping.hpp 0 → 100644 +129 −0 Original line number Diff line number Diff line /** * @file * @brief Definition of charge carrier detrapping models * * @copyright Copyright (c) 2021 CERN and the Allpix Squared authors. * This software is distributed under the terms of the MIT License, copied verbatim in the file "LICENSE.md". * In applying this license, CERN does not waive the privileges and immunities granted to it by virtue of its status as an * Intergovernmental Organization or submit itself to any jurisdiction. * SPDX-License-Identifier: MIT */ #ifndef ALLPIX_DETRAPPING_MODELS_H #define ALLPIX_DETRAPPING_MODELS_H #include <TFormula.h> #include "exceptions.h" #include "core/config/Configuration.hpp" #include "core/utils/log.h" #include "core/utils/unit.h" #include "objects/SensorCharge.hpp" namespace allpix { /** * @ingroup Models * @brief Charge carrier detrapping time models */ class DetrappingModel { public: /** * Default constructor */ DetrappingModel() = default; /** * Default virtual destructor */ virtual ~DetrappingModel() = default; /** * Function call operator to obtain detrapping time for the given carrier * @param type Type of charge carrier (electron or hole) * @param probability Current detrapping probability for this charge carrier * @param efield_mag Magnitude of the electric field * @return Expected time of the charge carrier being detrapped */ virtual double operator()(const CarrierType& type, double probability, double efield_mag) const = 0; }; /** * @ingroup Models * @brief No detrapping */ class NoDetrapping : virtual public DetrappingModel { public: double operator()(const CarrierType&, double, double) const override { return std::numeric_limits<double>::max(); }; }; /** * @ingroup Models * @brief Constant detrapping rate of charge carriers */ class ConstantDetrapping : virtual public DetrappingModel { public: ConstantDetrapping(double electron_lifetime, double hole_lifetime) : tau_eff_electron_(electron_lifetime), tau_eff_hole_(hole_lifetime){}; double operator()(const CarrierType& type, double probability, double) const override { return -1 * log(1 - probability) * (type == CarrierType::ELECTRON ? tau_eff_electron_ : tau_eff_hole_); } protected: double tau_eff_electron_{std::numeric_limits<double>::max()}; double tau_eff_hole_{std::numeric_limits<double>::max()}; }; /** * @brief Wrapper class and factory for detrapping models. * * This class allows to store detrapping objects independently of the model chosen and simplifies access to the * function call operator. The constructor acts as factory, generating model objects from the model name provided, e.g. * from a configuration file. */ class Detrapping { public: /** * Default constructor */ Detrapping() = default; /** * Detrapping model constructor * @param config Configuration of the calling module */ explicit Detrapping(const Configuration& config) { try { auto model = config.get<std::string>("detrapping_model", "none"); if(model == "constant") { model_ = std::make_unique<ConstantDetrapping>(config.get<double>("detrapping_time_electron"), config.get<double>("detrapping_time_hole")); } else if(model == "none") { LOG(INFO) << "No charge carrier detrapping model chosen, no detrapping simulated"; model_ = std::make_unique<NoDetrapping>(); } else { throw InvalidModelError(model); } } catch(const ModelError& e) { throw InvalidValueError(config, "detrapping_model", e.what()); } } /** * Function call operator forwarded to the detrapping model * @return Detrapping time */ template <class... ARGS> double operator()(ARGS&&... args) const { return model_->operator()(std::forward<ARGS>(args)...); } private: std::unique_ptr<DetrappingModel> model_{}; }; } // namespace allpix #endif src/physics/Trapping.hpp +13 −86 Original line number Diff line number Diff line Loading @@ -57,32 +57,6 @@ namespace allpix { double tau_eff_hole_{std::numeric_limits<double>::max()}; }; /** * @ingroup Models * @brief Charge carrier detrapping time models */ class DetrappingModel { public: /** * Default constructor */ DetrappingModel() = default; /** * Default virtual destructor */ virtual ~DetrappingModel() = default; /** * Function call operator to obtain trapping time for the given carrier * @param type Type of charge carrier (electron or hole) * @param probability Current trapping probability for this charge carrier * @param efield_mag Magnitude of the electric field * @return Expected time of the charge carrier being trapped */ virtual double operator()(const CarrierType& type, double probability, double, double efield_mag) const = 0; }; /** * @ingroup Models * @brief No trapping Loading @@ -92,17 +66,6 @@ namespace allpix { bool operator()(const CarrierType&, double, double, double) const override { return false; }; }; /** * @ingroup Models * @brief No detrapping */ class NoDetrapping : virtual public DetrappingModel { public: double operator()(const CarrierType&, double, double, double) const override { return std::numeric_limits<double>::max(); }; }; /** * @ingroup Models * @brief Constant trapping rate of charge carriers Loading @@ -115,24 +78,6 @@ namespace allpix { } }; /** * @ingroup Models * @brief Constant trapping rate of charge carriers */ class ConstantDetrapping : virtual public DetrappingModel { public: ConstantDetrapping(double electron_lifetime, double hole_lifetime) : tau_eff_electron_(electron_lifetime), tau_eff_hole_(hole_lifetime){}; double operator()(const CarrierType& type, double probability, double, double) const override { return -1 * log(1 - probability) * (type == CarrierType::ELECTRON ? tau_eff_electron_ : tau_eff_hole_); } protected: double tau_eff_electron_{std::numeric_limits<double>::max()}; double tau_eff_hole_{std::numeric_limits<double>::max()}; }; /** * @ingroup Models * @brief Ljubljana / Kramberger effective trapping model for charge carriers in silicon Loading Loading @@ -277,21 +222,21 @@ namespace allpix { } if(model == "ljubljana" || model == "kramberger") { model_trap_ = std::make_unique<Ljubljana>(temperature, fluence); model_ = std::make_unique<Ljubljana>(temperature, fluence); } else if(model == "dortmund" || model == "krasel") { model_trap_ = std::make_unique<Dortmund>(fluence); model_ = std::make_unique<Dortmund>(fluence); } else if(model == "cmstracker") { model_trap_ = std::make_unique<CMSTracker>(fluence); model_ = std::make_unique<CMSTracker>(fluence); } else if(model == "mandic") { model_trap_ = std::make_unique<Mandic>(fluence); model_ = std::make_unique<Mandic>(fluence); } else if(model == "constant") { model_trap_ = std::make_unique<ConstantTrapping>(config.get<double>("trapping_time_electron"), model_ = std::make_unique<ConstantTrapping>(config.get<double>("trapping_time_electron"), config.get<double>("trapping_time_hole")); } else if(model == "none") { LOG(INFO) << "No charge carrier trapping model chosen, no trapping simulated"; model_trap_ = std::make_unique<NoTrapping>(); model_ = std::make_unique<NoTrapping>(); } else if(model == "custom") { model_trap_ = std::make_unique<CustomTrapping>(config); model_ = std::make_unique<CustomTrapping>(config); } else { throw InvalidModelError(model); } Loading @@ -299,36 +244,18 @@ namespace allpix { } catch(const ModelError& e) { throw InvalidValueError(config, "trapping_model", e.what()); } try { auto model = config.get<std::string>("detrapping_model", "none"); if(model == "constant") { model_detrap_ = std::make_unique<ConstantDetrapping>(config.get<double>("detrapping_time_electron"), config.get<double>("detrapping_time_hole")); } else if(model == "none") { LOG(INFO) << "No charge carrier detrapping model chosen, no detrapping simulated"; model_detrap_ = std::make_unique<NoDetrapping>(); } else { throw InvalidModelError(model); } } catch(const ModelError& e) { throw InvalidValueError(config, "detrapping_model", e.what()); } } /** * Function call operator forwarded to the trapping and detrapping model * @return Trapping state and detrapping time * Function call operator forwarded to the trapping model * @return Trapping state */ template <class... ARGS> std::pair<bool, double> operator()(ARGS&&... args) const { return {model_trap_->operator()(std::forward<ARGS>(args)...), model_detrap_->operator()(std::forward<ARGS>(args)...)}; template <class... ARGS> bool operator()(ARGS&&... args) const { return model_->operator()(std::forward<ARGS>(args)...); } private: std::unique_ptr<TrappingModel> model_trap_{}; std::unique_ptr<DetrappingModel> model_detrap_{}; std::unique_ptr<TrappingModel> model_{}; }; } // namespace allpix Loading Loading
src/physics/Detrapping.hpp 0 → 100644 +129 −0 Original line number Diff line number Diff line /** * @file * @brief Definition of charge carrier detrapping models * * @copyright Copyright (c) 2021 CERN and the Allpix Squared authors. * This software is distributed under the terms of the MIT License, copied verbatim in the file "LICENSE.md". * In applying this license, CERN does not waive the privileges and immunities granted to it by virtue of its status as an * Intergovernmental Organization or submit itself to any jurisdiction. * SPDX-License-Identifier: MIT */ #ifndef ALLPIX_DETRAPPING_MODELS_H #define ALLPIX_DETRAPPING_MODELS_H #include <TFormula.h> #include "exceptions.h" #include "core/config/Configuration.hpp" #include "core/utils/log.h" #include "core/utils/unit.h" #include "objects/SensorCharge.hpp" namespace allpix { /** * @ingroup Models * @brief Charge carrier detrapping time models */ class DetrappingModel { public: /** * Default constructor */ DetrappingModel() = default; /** * Default virtual destructor */ virtual ~DetrappingModel() = default; /** * Function call operator to obtain detrapping time for the given carrier * @param type Type of charge carrier (electron or hole) * @param probability Current detrapping probability for this charge carrier * @param efield_mag Magnitude of the electric field * @return Expected time of the charge carrier being detrapped */ virtual double operator()(const CarrierType& type, double probability, double efield_mag) const = 0; }; /** * @ingroup Models * @brief No detrapping */ class NoDetrapping : virtual public DetrappingModel { public: double operator()(const CarrierType&, double, double) const override { return std::numeric_limits<double>::max(); }; }; /** * @ingroup Models * @brief Constant detrapping rate of charge carriers */ class ConstantDetrapping : virtual public DetrappingModel { public: ConstantDetrapping(double electron_lifetime, double hole_lifetime) : tau_eff_electron_(electron_lifetime), tau_eff_hole_(hole_lifetime){}; double operator()(const CarrierType& type, double probability, double) const override { return -1 * log(1 - probability) * (type == CarrierType::ELECTRON ? tau_eff_electron_ : tau_eff_hole_); } protected: double tau_eff_electron_{std::numeric_limits<double>::max()}; double tau_eff_hole_{std::numeric_limits<double>::max()}; }; /** * @brief Wrapper class and factory for detrapping models. * * This class allows to store detrapping objects independently of the model chosen and simplifies access to the * function call operator. The constructor acts as factory, generating model objects from the model name provided, e.g. * from a configuration file. */ class Detrapping { public: /** * Default constructor */ Detrapping() = default; /** * Detrapping model constructor * @param config Configuration of the calling module */ explicit Detrapping(const Configuration& config) { try { auto model = config.get<std::string>("detrapping_model", "none"); if(model == "constant") { model_ = std::make_unique<ConstantDetrapping>(config.get<double>("detrapping_time_electron"), config.get<double>("detrapping_time_hole")); } else if(model == "none") { LOG(INFO) << "No charge carrier detrapping model chosen, no detrapping simulated"; model_ = std::make_unique<NoDetrapping>(); } else { throw InvalidModelError(model); } } catch(const ModelError& e) { throw InvalidValueError(config, "detrapping_model", e.what()); } } /** * Function call operator forwarded to the detrapping model * @return Detrapping time */ template <class... ARGS> double operator()(ARGS&&... args) const { return model_->operator()(std::forward<ARGS>(args)...); } private: std::unique_ptr<DetrappingModel> model_{}; }; } // namespace allpix #endif
src/physics/Trapping.hpp +13 −86 Original line number Diff line number Diff line Loading @@ -57,32 +57,6 @@ namespace allpix { double tau_eff_hole_{std::numeric_limits<double>::max()}; }; /** * @ingroup Models * @brief Charge carrier detrapping time models */ class DetrappingModel { public: /** * Default constructor */ DetrappingModel() = default; /** * Default virtual destructor */ virtual ~DetrappingModel() = default; /** * Function call operator to obtain trapping time for the given carrier * @param type Type of charge carrier (electron or hole) * @param probability Current trapping probability for this charge carrier * @param efield_mag Magnitude of the electric field * @return Expected time of the charge carrier being trapped */ virtual double operator()(const CarrierType& type, double probability, double, double efield_mag) const = 0; }; /** * @ingroup Models * @brief No trapping Loading @@ -92,17 +66,6 @@ namespace allpix { bool operator()(const CarrierType&, double, double, double) const override { return false; }; }; /** * @ingroup Models * @brief No detrapping */ class NoDetrapping : virtual public DetrappingModel { public: double operator()(const CarrierType&, double, double, double) const override { return std::numeric_limits<double>::max(); }; }; /** * @ingroup Models * @brief Constant trapping rate of charge carriers Loading @@ -115,24 +78,6 @@ namespace allpix { } }; /** * @ingroup Models * @brief Constant trapping rate of charge carriers */ class ConstantDetrapping : virtual public DetrappingModel { public: ConstantDetrapping(double electron_lifetime, double hole_lifetime) : tau_eff_electron_(electron_lifetime), tau_eff_hole_(hole_lifetime){}; double operator()(const CarrierType& type, double probability, double, double) const override { return -1 * log(1 - probability) * (type == CarrierType::ELECTRON ? tau_eff_electron_ : tau_eff_hole_); } protected: double tau_eff_electron_{std::numeric_limits<double>::max()}; double tau_eff_hole_{std::numeric_limits<double>::max()}; }; /** * @ingroup Models * @brief Ljubljana / Kramberger effective trapping model for charge carriers in silicon Loading Loading @@ -277,21 +222,21 @@ namespace allpix { } if(model == "ljubljana" || model == "kramberger") { model_trap_ = std::make_unique<Ljubljana>(temperature, fluence); model_ = std::make_unique<Ljubljana>(temperature, fluence); } else if(model == "dortmund" || model == "krasel") { model_trap_ = std::make_unique<Dortmund>(fluence); model_ = std::make_unique<Dortmund>(fluence); } else if(model == "cmstracker") { model_trap_ = std::make_unique<CMSTracker>(fluence); model_ = std::make_unique<CMSTracker>(fluence); } else if(model == "mandic") { model_trap_ = std::make_unique<Mandic>(fluence); model_ = std::make_unique<Mandic>(fluence); } else if(model == "constant") { model_trap_ = std::make_unique<ConstantTrapping>(config.get<double>("trapping_time_electron"), model_ = std::make_unique<ConstantTrapping>(config.get<double>("trapping_time_electron"), config.get<double>("trapping_time_hole")); } else if(model == "none") { LOG(INFO) << "No charge carrier trapping model chosen, no trapping simulated"; model_trap_ = std::make_unique<NoTrapping>(); model_ = std::make_unique<NoTrapping>(); } else if(model == "custom") { model_trap_ = std::make_unique<CustomTrapping>(config); model_ = std::make_unique<CustomTrapping>(config); } else { throw InvalidModelError(model); } Loading @@ -299,36 +244,18 @@ namespace allpix { } catch(const ModelError& e) { throw InvalidValueError(config, "trapping_model", e.what()); } try { auto model = config.get<std::string>("detrapping_model", "none"); if(model == "constant") { model_detrap_ = std::make_unique<ConstantDetrapping>(config.get<double>("detrapping_time_electron"), config.get<double>("detrapping_time_hole")); } else if(model == "none") { LOG(INFO) << "No charge carrier detrapping model chosen, no detrapping simulated"; model_detrap_ = std::make_unique<NoDetrapping>(); } else { throw InvalidModelError(model); } } catch(const ModelError& e) { throw InvalidValueError(config, "detrapping_model", e.what()); } } /** * Function call operator forwarded to the trapping and detrapping model * @return Trapping state and detrapping time * Function call operator forwarded to the trapping model * @return Trapping state */ template <class... ARGS> std::pair<bool, double> operator()(ARGS&&... args) const { return {model_trap_->operator()(std::forward<ARGS>(args)...), model_detrap_->operator()(std::forward<ARGS>(args)...)}; template <class... ARGS> bool operator()(ARGS&&... args) const { return model_->operator()(std::forward<ARGS>(args)...); } private: std::unique_ptr<TrappingModel> model_trap_{}; std::unique_ptr<DetrappingModel> model_detrap_{}; std::unique_ptr<TrappingModel> model_{}; }; } // namespace allpix Loading