Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-02-22 10:31:28

0001 //----------------------------------*-C++-*----------------------------------//
0002 // Copyright 2021-2024 UT-Battelle, LLC, and other Celeritas developers.
0003 // See the top-level COPYRIGHT file for details.
0004 // SPDX-License-Identifier: (Apache-2.0 OR MIT)
0005 //---------------------------------------------------------------------------//
0006 //! \file celeritas/phys/ImportedProcessAdapter.hh
0007 //---------------------------------------------------------------------------//
0008 #pragma once
0009 
0010 #include <algorithm>
0011 #include <initializer_list>
0012 #include <map>
0013 #include <memory>
0014 #include <utility>
0015 #include <vector>
0016 
0017 #include "corecel/Assert.hh"
0018 #include "corecel/OpaqueId.hh"
0019 #include "corecel/cont/Span.hh"
0020 #include "celeritas/Types.hh"
0021 #include "celeritas/grid/ValueGridBuilder.hh"
0022 #include "celeritas/io/ImportPhysicsTable.hh"
0023 #include "celeritas/io/ImportProcess.hh"
0024 
0025 #include "Applicability.hh"
0026 #include "PDGNumber.hh"
0027 #include "Process.hh"
0028 
0029 namespace celeritas
0030 {
0031 class ParticleParams;
0032 struct ImportData;
0033 //---------------------------------------------------------------------------//
0034 //! Small helper class to hopefully help a little with debugging errors
0035 class IPAContextException : public RichContextException
0036 {
0037   public:
0038     IPAContextException(ParticleId id, ImportProcessClass ipc, MaterialId mid);
0039 
0040     //! This class type
0041     char const* type() const final { return "ImportProcessAdapterContext"; }
0042 
0043     // Save context to a JSON object
0044     void output(JsonPimpl*) const final {}
0045 
0046     //! Get an explanatory message
0047     char const* what() const noexcept final { return what_.c_str(); }
0048 
0049   private:
0050     std::string what_;
0051 };
0052 
0053 //---------------------------------------------------------------------------//
0054 /*!
0055  * Manage imported physics data.
0056  */
0057 class ImportedProcesses
0058 {
0059   public:
0060     //!@{
0061     //! \name Type aliases
0062     using ImportProcessId = OpaqueId<ImportProcess>;
0063     using key_type = std::pair<PDGNumber, ImportProcessClass>;
0064     using SPConstParticles = std::shared_ptr<ParticleParams const>;
0065     //!@}
0066 
0067   public:
0068     // Construct with imported data
0069     static std::shared_ptr<ImportedProcesses>
0070     from_import(ImportData const& data, SPConstParticles particle_params);
0071 
0072     // Construct with imported tables
0073     explicit ImportedProcesses(std::vector<ImportProcess> io);
0074 
0075     // Return physics tables for a particle type and process
0076     ImportProcessId find(key_type) const;
0077 
0078     // Get the table for the given process ID
0079     inline ImportProcess const& get(ImportProcessId id) const;
0080 
0081     // Number of imported processes
0082     inline ImportProcessId::size_type size() const;
0083 
0084   private:
0085     std::vector<ImportProcess> processes_;
0086     std::map<key_type, ImportProcessId> ids_;
0087 };
0088 
0089 //---------------------------------------------------------------------------//
0090 /*!
0091  * Construct step limits from imported physics data.
0092  */
0093 class ImportedProcessAdapter
0094 {
0095   public:
0096     //!@{
0097     //! \name Type aliases
0098     using SPConstImported = std::shared_ptr<ImportedProcesses const>;
0099     using SPConstParticles = std::shared_ptr<ParticleParams const>;
0100     using StepLimitBuilders = Process::StepLimitBuilders;
0101     using SpanConstPDG = Span<PDGNumber const>;
0102     //!@}
0103 
0104   public:
0105     // Construct from shared table data
0106     ImportedProcessAdapter(SPConstImported imported,
0107                            SPConstParticles const& particles,
0108                            ImportProcessClass process_class,
0109                            SpanConstPDG pdg_numbers);
0110 
0111     // Construct from shared table data
0112     ImportedProcessAdapter(SPConstImported imported,
0113                            SPConstParticles const& particles,
0114                            ImportProcessClass process_class,
0115                            std::initializer_list<PDGNumber> pdg_numbers);
0116 
0117     // Construct step limits from the given particle/material type
0118     StepLimitBuilders step_limits(Applicability const& applic) const;
0119 
0120     // Get the lambda table for the given particle ID
0121     inline ImportPhysicsTable const& get_lambda(ParticleId id) const;
0122 
0123     // Access the imported processes
0124     SPConstImported const& processes() const { return imported_; }
0125 
0126     // Whether the given model is present in the process
0127     inline bool has_model(PDGNumber, ImportModelClass) const;
0128 
0129   private:
0130     using ImportTableId = OpaqueId<ImportPhysicsTable>;
0131     using ImportProcessId = ImportedProcesses::ImportProcessId;
0132 
0133     struct ParticleProcessIds
0134     {
0135         ImportProcessId process;
0136         ImportTableId lambda;
0137         ImportTableId lambda_prim;
0138         ImportTableId dedx;
0139         ImportTableId range;
0140     };
0141 
0142     SPConstImported imported_;
0143     ImportProcessClass process_class_;
0144     std::map<ParticleId, ParticleProcessIds> ids_;
0145 
0146     // Construct step limits from the given particle/material type
0147     StepLimitBuilders step_limits_impl(Applicability const& applic) const;
0148 };
0149 
0150 //---------------------------------------------------------------------------//
0151 // INLINE DEFINITIONS
0152 //---------------------------------------------------------------------------//
0153 /*!
0154  * Get the table for the given process ID.
0155  */
0156 ImportProcess const& ImportedProcesses::get(ImportProcessId id) const
0157 {
0158     CELER_EXPECT(id < this->size());
0159     return processes_[id.get()];
0160 }
0161 
0162 //---------------------------------------------------------------------------//
0163 /*!
0164  * Number of imported processes.
0165  */
0166 auto ImportedProcesses::size() const -> ImportProcessId::size_type
0167 {
0168     return processes_.size();
0169 }
0170 
0171 //---------------------------------------------------------------------------//
0172 /*!
0173  * Get cross sections for the given particle ID.
0174  *
0175  * This is currently used for loading MSC data for calculating mean free paths.
0176  */
0177 ImportPhysicsTable const&
0178 ImportedProcessAdapter::get_lambda(ParticleId id) const
0179 {
0180     auto iter = ids_.find(id);
0181     CELER_EXPECT(iter != ids_.end());
0182     ImportTableId tab = iter->second.lambda;
0183     CELER_ENSURE(tab);
0184     return imported_->get(iter->second.process).tables[tab.unchecked_get()];
0185 }
0186 
0187 //---------------------------------------------------------------------------//
0188 /*!
0189  * Whether the given model is present in the process.
0190  */
0191 bool ImportedProcessAdapter::has_model(PDGNumber pdg, ImportModelClass imc) const
0192 {
0193     auto const& models
0194         = imported_->get(imported_->find({pdg, process_class_})).models;
0195     return std::any_of(
0196         models.begin(), models.end(), [&imc](ImportModel const& m) {
0197             return m.model_class == imc;
0198         });
0199 }
0200 
0201 //---------------------------------------------------------------------------//
0202 }  // namespace celeritas