Line data Source code
1 : // SPDX-FileCopyrightText: 2024 Pairinteraction Developers 2 : // SPDX-License-Identifier: LGPL-3.0-or-later 3 : 4 : #include "pairinteraction/basis/BasisAtomCreator.hpp" 5 : 6 : #include "pairinteraction/database/AtomDescriptionByRanges.hpp" 7 : #include "pairinteraction/database/Database.hpp" 8 : #include "pairinteraction/enums/Parity.hpp" 9 : #include "pairinteraction/ket/KetAtom.hpp" 10 : 11 : namespace pairinteraction { 12 : template <typename Scalar> 13 84 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::set_species(const std::string &value) { 14 84 : species.emplace(value); 15 84 : return *this; 16 : } 17 : 18 : template <typename Scalar> 19 27 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_energy(real_t min, real_t max) { 20 27 : range_energy = {min, max}; 21 27 : return *this; 22 : } 23 : 24 : template <typename Scalar> 25 0 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_quantum_number_f(real_t min, 26 : real_t max) { 27 0 : if (2 * min != std::rint(2 * min) || 2 * max != std::rint(2 * max)) { 28 0 : throw std::invalid_argument("Quantum number f must be an integer or half-integer."); 29 : } 30 0 : range_quantum_number_f = {min, max}; 31 0 : return *this; 32 : } 33 : 34 : template <typename Scalar> 35 31 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_quantum_number_m(real_t min, 36 : real_t max) { 37 31 : if (2 * min != std::rint(2 * min) || 2 * max != std::rint(2 * max)) { 38 0 : throw std::invalid_argument("Quantum number m must be an integer or half-integer."); 39 : } 40 31 : range_quantum_number_m = {min, max}; 41 31 : return *this; 42 : } 43 : 44 : template <typename Scalar> 45 0 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_parity(Parity value) { 46 0 : parity = value; 47 0 : return *this; 48 : } 49 : 50 : template <typename Scalar> 51 70 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_quantum_number_n(int min, int max) { 52 70 : range_quantum_number_n = {min, max}; 53 70 : return *this; 54 : } 55 : 56 : template <typename Scalar> 57 3 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_quantum_number_nu(real_t min, 58 : real_t max) { 59 3 : range_quantum_number_nu = {min, max}; 60 3 : return *this; 61 : } 62 : 63 : template <typename Scalar> 64 0 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_quantum_number_nui(real_t min, 65 : real_t max) { 66 0 : range_quantum_number_nui = {min, max}; 67 0 : return *this; 68 : } 69 : 70 : template <typename Scalar> 71 72 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_quantum_number_l(real_t min, 72 : real_t max) { 73 72 : range_quantum_number_l = {min, max}; 74 72 : return *this; 75 : } 76 : 77 : template <typename Scalar> 78 0 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_quantum_number_s(real_t min, 79 : real_t max) { 80 0 : range_quantum_number_s = {min, max}; 81 0 : return *this; 82 : } 83 : 84 : template <typename Scalar> 85 0 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_quantum_number_j(real_t min, 86 : real_t max) { 87 0 : range_quantum_number_j = {min, max}; 88 0 : return *this; 89 : } 90 : 91 : template <typename Scalar> 92 0 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_quantum_number_l_ryd(real_t min, 93 : real_t max) { 94 0 : range_quantum_number_l_ryd = {min, max}; 95 0 : return *this; 96 : } 97 : 98 : template <typename Scalar> 99 0 : BasisAtomCreator<Scalar> &BasisAtomCreator<Scalar>::restrict_quantum_number_j_ryd(real_t min, 100 : real_t max) { 101 0 : range_quantum_number_j_ryd = {min, max}; 102 0 : return *this; 103 : } 104 : 105 : template <typename Scalar> 106 : BasisAtomCreator<Scalar> & 107 50 : BasisAtomCreator<Scalar>::append_ket(const std::shared_ptr<const ket_t> &ket) { 108 65 : if (additional_ket_species.has_value() && 109 15 : additional_ket_species.value() != ket->get_species()) { 110 0 : throw std::invalid_argument("Species mismatch."); 111 : } 112 50 : additional_ket_species.emplace(ket->get_species()); 113 50 : additional_ket_ids.push_back(ket->get_id_in_database()); 114 50 : return *this; 115 : } 116 : 117 : template <typename Scalar> 118 : std::shared_ptr<const BasisAtom<Scalar>> 119 86 : BasisAtomCreator<Scalar>::create(Database &database) const { 120 : 121 119 : if (species.has_value() && additional_ket_species.has_value() && 122 33 : species.value() != additional_ket_species.value()) { 123 0 : throw std::invalid_argument("Species mismatch."); 124 : } 125 : 126 86 : std::string extracted_species; 127 86 : if (species.has_value()) { 128 84 : extracted_species = species.value(); 129 2 : } else if (additional_ket_species.has_value()) { 130 2 : extracted_species = additional_ket_species.value(); 131 : } else { 132 0 : throw std::runtime_error("Species not set."); 133 : } 134 : 135 86 : AtomDescriptionByRanges description{parity, 136 : range_energy, 137 : range_quantum_number_f, 138 : range_quantum_number_m, 139 : range_quantum_number_n, 140 : range_quantum_number_nu, 141 : range_quantum_number_nui, 142 : range_quantum_number_l, 143 : range_quantum_number_s, 144 : range_quantum_number_j, 145 : range_quantum_number_l_ryd, 146 : range_quantum_number_j_ryd}; 147 : 148 172 : return database.get_basis<Scalar>(extracted_species, description, additional_ket_ids); 149 86 : } 150 : 151 : // Explicit instantiations 152 : template class BasisAtomCreator<double>; 153 : template class BasisAtomCreator<std::complex<double>>; 154 : } // namespace pairinteraction