Back to home page

EIC code displayed by LXR

 
 

    


Warning, file /acts/Core/src/Material/Material.cpp was not indexed or was modified since last indexation (in which case cross-reference links may be missing, inaccurate or erroneous).

0001 // This file is part of the ACTS project.
0002 //
0003 // Copyright (C) 2016 CERN for the benefit of the ACTS project
0004 //
0005 // This Source Code Form is subject to the terms of the Mozilla Public
0006 // License, v. 2.0. If a copy of the MPL was not distributed with this
0007 // file, You can obtain one at https://mozilla.org/MPL/2.0/.
0008 
0009 #include "Acts/Material/Material.hpp"
0010 
0011 #include "Acts/Definitions/Units.hpp"
0012 
0013 #include <cmath>
0014 #include <ostream>
0015 
0016 namespace Acts {
0017 
0018 namespace {
0019 enum MaterialClassificationNumberIndices {
0020   eRadiationLength = 0,
0021   eInteractionLength = 1,
0022   eRelativeAtomicMass = 2,
0023   eNuclearCharge = 3,
0024   eMolarDensity = 4,
0025 };
0026 
0027 constexpr float calculateMolarElectronDensity(float z, float molarRho) {
0028   return z * molarRho;
0029 }
0030 
0031 constexpr float approximateMeanExcitationEnergy(float z) {
0032   using namespace UnitLiterals;
0033 
0034   // use approximative computation as defined in ATL-SOFT-PUB-2008-003
0035   return 16_eV * std::pow(z, 0.9f);
0036 }
0037 }  // namespace
0038 
0039 Material Material::fromMassDensity(float x0, float l0, float ar, float z,
0040                                    float massRho) {
0041   using namespace UnitLiterals;
0042 
0043   // mass density is defined as
0044   //
0045   //     mass-density = atomic-mass * number-of-atoms / volume
0046   //                  = atomic-mass * molar-density * avogadro-constant
0047   // -> molar-density = mass-density / (atomic-mass * avogadro-constant)
0048   //
0049   // with the atomic mass given by
0050   //
0051   //      atomic-mass = relative-atomic-mass * atomic-mass-unit
0052   //
0053   // perform computations in double precision to avoid loss of precision
0054   const double atomicMass = static_cast<double>(ar) * 1_u;
0055   float molarRho =
0056       static_cast<float>(massRho / (atomicMass * PhysicalConstants::kAvogadro));
0057 
0058   return Material::fromMolarDensity(x0, l0, ar, z, molarRho);
0059 }
0060 
0061 Material Material::fromMolarDensity(float x0, float l0, float ar, float z,
0062                                     float molarRho) {
0063   return Material::fromMolarDensity(x0, l0, ar, z, molarRho,
0064                                     calculateMolarElectronDensity(z, molarRho),
0065                                     std::nullopt);
0066 }
0067 
0068 Material Material::fromMolarDensity(float x0, float l0, float ar, float z,
0069                                     float molarRho, float molarElectronRho,
0070                                     std::optional<float> meanExcitationEnergy) {
0071   Material mat;
0072   mat.m_x0 = x0;
0073   mat.m_l0 = l0;
0074   mat.m_ar = ar;
0075   mat.m_z = z;
0076   mat.m_molarRho = molarRho;
0077   mat.m_molarElectronRho = molarElectronRho;
0078   mat.m_meanExcitationEnergy =
0079       meanExcitationEnergy.value_or(approximateMeanExcitationEnergy(z));
0080   return mat;
0081 }
0082 
0083 Material::Material(const ParametersVector& parameters)
0084     : m_x0(parameters[eRadiationLength]),
0085       m_l0(parameters[eInteractionLength]),
0086       m_ar(parameters[eRelativeAtomicMass]),
0087       m_z(parameters[eNuclearCharge]),
0088       m_molarRho(parameters[eMolarDensity]),
0089       m_molarElectronRho(calculateMolarElectronDensity(m_z, m_molarRho)),
0090       m_meanExcitationEnergy(approximateMeanExcitationEnergy(m_z)) {}
0091 
0092 float Material::massDensity() const {
0093   using namespace UnitLiterals;
0094 
0095   // perform computations in double precision to avoid loss of precision
0096   const double atomicMass = static_cast<double>(m_ar) * 1_u;
0097   const double numberDensity =
0098       static_cast<double>(m_molarRho) * PhysicalConstants::kAvogadro;
0099   return atomicMass * numberDensity;
0100 }
0101 
0102 Material::ParametersVector Material::parameters() const {
0103   ParametersVector parameters;
0104   parameters[eRadiationLength] = m_x0;
0105   parameters[eInteractionLength] = m_l0;
0106   parameters[eRelativeAtomicMass] = m_ar;
0107   parameters[eNuclearCharge] = m_z;
0108   parameters[eMolarDensity] = m_molarRho;
0109   return parameters;
0110 }
0111 
0112 std::ostream& operator<<(std::ostream& os, const Material& material) {
0113   if (material.isVacuum()) {
0114     os << "vacuum";
0115   } else {
0116     os << "x0=" << material.X0();
0117     os << "|l0=" << material.L0();
0118     os << "|ar=" << material.Ar();
0119     os << "|z=" << material.Z();
0120     os << "|molar_rho=" << material.molarDensity();
0121     os << "|molar_e_rho=" << material.molarElectronDensity();
0122     os << "|mean_excitation_energy=" << material.meanExcitationEnergy();
0123   }
0124   return os;
0125 }
0126 
0127 }  // namespace Acts