Skip to content

Commit e80b9d2

Browse files
Introduce wavefunction_traits, move most bitset-specific logic into template specialization
1 parent e17fc9d commit e80b9d2

16 files changed

+430
-270
lines changed

include/macis/asci/determinant_contributions.hpp

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@ void append_singles_asci_contributions(
3636
const double* V_kpq, const size_t LDV, double h_el_tol, double root_diag,
3737
double E0, const HamiltonianGeneratorBase<double>& ham_gen,
3838
asci_contrib_container<WfnType>& asci_contributions) {
39+
using wfn_traits = wavefunction_traits<WfnType>;
3940
const auto LDG2 = LDG * LDG;
4041
const auto LDV2 = LDV * LDV;
4142
for(auto i : occ_same)
@@ -51,7 +52,7 @@ void append_singles_asci_contributions(
5152
if(std::abs(h_el) < h_el_tol) continue;
5253

5354
// Calculate Excited Determinant
54-
auto ex_det = single_excitation_spin<Sigma>(state_full, i, a);
55+
auto ex_det = wfn_traits::template single_excitation_no_check<Sigma>(state_full, i, a);
5556

5657
// Calculate Excitation Sign in a Canonical Way
5758
auto sign = single_excitation_sign(state_same, a, i);
@@ -77,6 +78,8 @@ void append_ss_doubles_asci_contributions(
7778
const double* G, size_t LDG, double h_el_tol, double root_diag, double E0,
7879
const HamiltonianGeneratorBase<double>& ham_gen,
7980
asci_contrib_container<WfnType>& asci_contributions) {
81+
using wfn_traits = wavefunction_traits<WfnType>;
82+
using spin_wfn_traits = wavefunction_traits<SpinWfnType>;
8083
const size_t nocc = ss_occ.size();
8184
const size_t nvir = vir.size();
8285

@@ -111,14 +114,14 @@ void append_ss_doubles_asci_contributions(
111114
// TODO: Can this be made faster since the orbital indices are known
112115
// in advance?
113116
// Compute excited determinant (spin)
114-
const auto full_ex_spin = double_excitation(SpinWfnType(0), i,j,a,b);
117+
const auto full_ex_spin = spin_wfn_traits::double_excitation_no_check(SpinWfnType(0), i,j,a,b);
115118
const auto ex_det_spin = state_same ^ full_ex_spin;
116119

117120
// Calculate the sign in a canonical way
118121
double sign = doubles_sign(state_same, ex_det_spin, full_ex_spin);
119122

120123
// Calculate full excited determinant
121-
auto ex_det = from_spin_safe<Sigma>(ex_det_spin, state_other);
124+
auto ex_det = wfn_traits::template from_spin<Sigma>(ex_det_spin, state_other);
122125
#endif
123126

124127
// Update sign of matrix element
@@ -147,6 +150,7 @@ void append_os_doubles_asci_contributions(
147150
const double* eps_beta, const double* V, size_t LDV, double h_el_tol,
148151
double root_diag, double E0, const HamiltonianGeneratorBase<double>& ham_gen,
149152
asci_contrib_container<WfnType>& asci_contributions) {
153+
using wfn_traits = wavefunction_traits<WfnType>;
150154
const size_t LDV2 = LDV * LDV;
151155
for(auto i : occ_alpha)
152156
for(auto a : vir_alpha) {
@@ -164,8 +168,8 @@ void append_os_doubles_asci_contributions(
164168
double sign = sign_alpha * sign_beta;
165169
//auto ex_det = state_full;
166170
//ex_det.flip(a).flip(i).flip(j + N).flip(b + N);
167-
auto ex_det = single_excitation_spin<Spin::Alpha>(state_full, a, i);
168-
ex_det = single_excitation_spin<Spin::Beta>(ex_det, b, j);
171+
auto ex_det = wfn_traits::template single_excitation_no_check<Spin::Alpha>(state_full, a, i);
172+
ex_det = wfn_traits::template single_excitation_no_check<Spin::Beta>(ex_det, b, j);
169173
auto h_el = sign * V_aibj;
170174

171175
// Evaluate fast diagonal element

include/macis/asci/determinant_search.hpp

Lines changed: 15 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,9 @@ asci_contrib_container<wfn_t<N>> asci_contributions_standard(
5757
const std::vector<double>& C, size_t norb, const double* T_pq,
5858
const double* G_red, const double* V_red, const double* G_pqrs,
5959
const double* V_pqrs, HamiltonianGenerator<wfn_t<N>>& ham_gen) {
60+
using wfn_traits = wavefunction_traits<wfn_t<N>>;
61+
using spin_wfn_type = spin_wfn_t<wfn_t<N>>;
62+
using spin_wfn_traits = wavefunction_traits<spin_wfn_type>;
6063
auto logger = spdlog::get("asci_search");
6164

6265
const size_t ncdets = std::distance(cdets_begin, cdets_end);
@@ -68,13 +71,13 @@ asci_contrib_container<wfn_t<N>> asci_contributions_standard(
6871
for(size_t i = 0; i < ncdets; ++i) {
6972
// Alias state data
7073
auto state = *(cdets_begin + i);
71-
auto state_alpha = bitset_lo_word(state);
72-
auto state_beta = bitset_hi_word(state);
74+
auto state_alpha = wfn_traits::alpha_string(state);
75+
auto state_beta = wfn_traits::beta_string(state);
7376
auto coeff = C[i];
7477

7578
// Get occupied and virtual indices
76-
bitset_to_occ_vir(norb, state_alpha, occ_alpha, vir_alpha);
77-
bitset_to_occ_vir(norb, state_beta, occ_beta, vir_beta);
79+
spin_wfn_traits::state_to_occ_vir(norb, state_alpha, occ_alpha, vir_alpha);
80+
spin_wfn_traits::state_to_occ_vir(norb, state_beta, occ_beta, vir_beta);
7881

7982
// Precompute orbital energies
8083
auto eps_alpha = ham_gen.single_orbital_ens(norb, occ_alpha, occ_beta);
@@ -150,6 +153,9 @@ asci_contrib_container<wfn_t<N>> asci_contributions_constraint(
150153
const double* V_pqrs, HamiltonianGenerator<wfn_t<N>>& ham_gen, MPI_Comm comm) {
151154
using clock_type = std::chrono::high_resolution_clock;
152155
using duration_type = std::chrono::duration<double, std::milli>;
156+
using wfn_traits = wavefunction_traits<wfn_t<N>>;
157+
using spin_wfn_type = spin_wfn_t<wfn_t<N>>;
158+
using spin_wfn_traits = wavefunction_traits<spin_wfn_type>;
153159

154160
auto logger = spdlog::get("asci_search");
155161
const size_t ncdets = std::distance(cdets_begin, cdets_end);
@@ -195,7 +201,7 @@ asci_contrib_container<wfn_t<N>> asci_contributions_constraint(
195201
h_diag = ham_gen.matrix_element(w, w);
196202

197203
// Compute occ/vir for beta string
198-
bitset_to_occ_vir(norb, beta_shift, occ_beta, vir_beta);
204+
wfn_traits::state_to_occ_vir(norb, beta_shift, occ_beta, vir_beta);
199205

200206
// Precompute orbital energies
201207
orb_ens_alpha = ham_gen.single_orbital_ens(norb, occ_alpha, occ_beta);
@@ -211,7 +217,7 @@ asci_contrib_container<wfn_t<N>> asci_contributions_constraint(
211217
for(auto i = 0; i < nuniq_alpha; ++i) {
212218
const auto wfn_a = uniq_alpha_wfn[i];
213219
std::vector<uint32_t> occ_alpha, vir_alpha;
214-
bitset_to_occ_vir(norb, wfn_a, occ_alpha, vir_alpha);
220+
wfn_traits::state_to_occ_vir(norb, wfn_a, occ_alpha, vir_alpha);
215221
for(auto j = 0; j < ncdets; ++j) {
216222
const auto w = *(cdets_begin + j);
217223
if((w & full_mask<N / 2, N>()) == wfn_a) {
@@ -223,7 +229,7 @@ asci_contrib_container<wfn_t<N>> asci_contributions_constraint(
223229
auto world_rank = comm_rank(comm);
224230
auto world_size = comm_size(comm);
225231

226-
const auto n_occ_alpha = uniq_alpha_wfn[0].count();
232+
const auto n_occ_alpha = wfn_traits::count(uniq_alpha_wfn[0]);
227233
const auto n_vir_alpha = norb - n_occ_alpha;
228234
const auto n_sing_alpha = n_occ_alpha * n_vir_alpha;
229235
const auto n_doub_alpha = (n_sing_alpha * (n_sing_alpha - norb + 1)) / 4;
@@ -335,8 +341,8 @@ asci_contrib_container<wfn_t<N>> asci_contributions_constraint(
335341
const auto& eps_beta = bcd.orb_ens_beta;
336342

337343
const auto state = det | beta;
338-
const auto state_alpha = alpha_string(state);
339-
const auto state_beta = beta_string(beta);
344+
const auto state_alpha = wfn_traits::alpha_string(state);
345+
const auto state_beta = wfn_traits::beta_string(beta);
340346
// BB Excitations
341347
append_singles_asci_contributions<Spin::Beta>(
342348
coeff, state, state_beta, occ_beta, vir_beta, occ_alpha,

include/macis/asci/mask_constraints.hpp

Lines changed: 15 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -249,7 +249,8 @@ void generate_constraint_singles_contributions_ss(
249249
const double* V_kpq, const size_t LDV, double h_el_tol, double root_diag,
250250
double E0, HamiltonianGeneratorBase<double>& ham_gen,
251251
asci_contrib_container<WfnType>& asci_contributions) {
252-
auto [o, v] = generate_constraint_single_excitations(alpha_string(det), alpha_string(T), alpha_string(O), alpha_string(B));
252+
using wfn_traits = wavefunction_traits<WfnType>;
253+
auto [o, v] = generate_constraint_single_excitations(wfn_traits::alpha_string(det), wfn_traits::alpha_string(T), wfn_traits::alpha_string(O), wfn_traits::alpha_string(B));
253254
const auto no = o.count();
254255
const auto nv = v.count();
255256
if(!no or !nv) return;
@@ -274,7 +275,7 @@ void generate_constraint_singles_contributions_ss(
274275
if(std::abs(coeff * h_el) < h_el_tol) continue;
275276

276277
// Calculate Excited Determinant
277-
auto ex_det = single_excitation_spin<Spin::Alpha>(det, i, a );
278+
auto ex_det = wfn_traits::template single_excitation_no_check<Spin::Alpha>(det, i, a );
278279

279280

280281
// Compute Sign in a Canonical Way
@@ -298,7 +299,9 @@ void generate_constraint_doubles_contributions_ss(
298299
const size_t LDG, double h_el_tol, double root_diag, double E0,
299300
HamiltonianGeneratorBase<double>& ham_gen,
300301
asci_contrib_container<WfnType>& asci_contributions) {
301-
auto [O, V] = generate_constraint_double_excitations(alpha_string(det), alpha_string(T), alpha_string(O_mask), alpha_string(B));
302+
using wfn_traits = wavefunction_traits<WfnType>;
303+
using spin_wfn_traits = wavefunction_traits<spin_wfn_t<WfnType>>;
304+
auto [O, V] = generate_constraint_double_excitations(wfn_traits::alpha_string(det), wfn_traits::alpha_string(T), wfn_traits::alpha_string(O_mask), wfn_traits::alpha_string(B));
302305
const auto no_pairs = O.size();
303306
const auto nv_pairs = V.size();
304307
if(!no_pairs or !nv_pairs) return;
@@ -309,7 +312,7 @@ void generate_constraint_doubles_contributions_ss(
309312
const auto i = ffs(ij) - 1;
310313
const auto j = fls(ij);
311314
const auto G_ij = G + (j + i * LDG2) * LDG;
312-
const auto ex_ij = single_excitation_spin<Spin::Alpha>(det,i,j); // det ^ ij;
315+
const auto ex_ij = wfn_traits::template single_excitation_no_check<Spin::Alpha>(det,i,j); // det ^ ij;
313316
for(int _ab = 0; _ab < nv_pairs; ++_ab) {
314317
const auto ab = V[_ab];
315318
const auto a = ffs(ab) - 1;
@@ -321,11 +324,11 @@ void generate_constraint_doubles_contributions_ss(
321324
if(std::abs(coeff * G_aibj) < h_el_tol) continue;
322325

323326
// Calculate Excited Determinant (spin)
324-
const auto full_ex_spin = single_excitation_spin<Spin::Alpha>(ij,a,b); // ij | ab;
325-
const auto ex_det_spin = single_excitation_spin<Spin::Alpha>(ex_ij,a,b); // ex_ij | ab;
327+
const auto full_ex_spin = spin_wfn_traits::template single_excitation_no_check<Spin::Alpha>(ij,a,b); // ij | ab;
328+
const auto ex_det_spin = wfn_traits::template single_excitation_no_check<Spin::Alpha>(ex_ij,a,b); // ex_ij | ab;
326329

327330
// Compute Sign in a Canonical Way
328-
auto sign = doubles_sign(alpha_string(det), alpha_string(ex_det_spin), full_ex_spin);
331+
auto sign = doubles_sign(wfn_traits::alpha_string(det), wfn_traits::alpha_string(ex_det_spin), full_ex_spin);
329332

330333
// Calculate Full Excited Determinant
331334
const auto full_ex = ex_det_spin;// | os_det;
@@ -352,8 +355,9 @@ void generate_constraint_doubles_contributions_os(
352355
const double* eps_othr, const double* V, const size_t LDV, double h_el_tol,
353356
double root_diag, double E0, HamiltonianGeneratorBase<double>& ham_gen,
354357
asci_contrib_container<WfnType>& asci_contributions) {
358+
using wfn_traits = wavefunction_traits<WfnType>;
355359
// Generate Single Excitations that Satisfy the Constraint
356-
auto [o, v] = generate_constraint_single_excitations(alpha_string(det), alpha_string(T), alpha_string(O), alpha_string(B));
360+
auto [o, v] = generate_constraint_single_excitations(wfn_traits::alpha_string(det), wfn_traits::alpha_string(T), wfn_traits::alpha_string(O), wfn_traits::alpha_string(B));
357361
const auto no = o.count();
358362
const auto nv = v.count();
359363
if(!no or !nv) return;
@@ -381,14 +385,14 @@ void generate_constraint_doubles_contributions_os(
381385
// double sign_othr = single_excitation_sign( os_det >> (N/2), b, j
382386
// );
383387
double sign_othr =
384-
single_excitation_sign(beta_string(det), b, j);
388+
single_excitation_sign(wfn_traits::beta_string(det), b, j);
385389
double sign = sign_same * sign_othr;
386390

387391
// Compute Excited Determinant
388392
//auto ex_det = det | os_det;
389393
//ex_det.flip(i).flip(a).flip(j + N / 2).flip(b + N / 2);
390-
auto ex_det = single_excitation_spin<Spin::Alpha>(det,i,a);
391-
ex_det = single_excitation_spin<Spin::Beta>(ex_det,j,b);
394+
auto ex_det = wfn_traits::template single_excitation_no_check<Spin::Alpha>(det,i,a);
395+
ex_det = wfn_traits::template single_excitation_no_check<Spin::Beta>(ex_det,j,b);
392396

393397
// Finalize Matrix Element
394398
auto h_el = sign * V_aibj;

include/macis/asci/pt2.hpp

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@ double asci_pt2_constraint(
2323

2424
using clock_type = std::chrono::high_resolution_clock;
2525
using duration_type = std::chrono::duration<double, std::milli>;
26+
using wfn_traits = wavefunction_traits<wfn_t<N>>;
2627

2728
auto logger = spdlog::get("asci_search");
2829
const size_t ncdets = std::distance(cdets_begin, cdets_end);
@@ -69,7 +70,7 @@ double asci_pt2_constraint(
6970
h_diag = ham_gen.matrix_element(w, w);
7071

7172
// Compute occ/vir for beta string
72-
bitset_to_occ_vir(norb, beta_shift, occ_beta, vir_beta);
73+
wfn_traits::state_to_occ_vir(norb, beta_shift, occ_beta, vir_beta);
7374

7475
// Precompute orbital energies
7576
orb_ens_alpha = ham_gen.single_orbital_ens(norb, occ_alpha, occ_beta);
@@ -85,7 +86,7 @@ double asci_pt2_constraint(
8586
for(auto i = 0; i < nuniq_alpha; ++i) {
8687
const auto wfn_a = uniq_alpha_wfn[i];
8788
std::vector<uint32_t> occ_alpha, vir_alpha;
88-
bitset_to_occ_vir(norb, wfn_a, occ_alpha, vir_alpha);
89+
wfn_traits::state_to_occ_vir(norb, wfn_a, occ_alpha, vir_alpha);
8990
for(auto j = 0; j < ncdets; ++j) {
9091
const auto w = *(cdets_begin + j);
9192
if((w & full_mask<N / 2, N>()) == wfn_a) {
@@ -97,7 +98,7 @@ double asci_pt2_constraint(
9798
auto world_rank = comm_rank(comm);
9899
auto world_size = comm_size(comm);
99100

100-
const auto n_occ_alpha = uniq_alpha_wfn[0].count();
101+
const auto n_occ_alpha = wfn_traits::count(uniq_alpha_wfn[0]);
101102
const auto n_vir_alpha = norb - n_occ_alpha;
102103
const auto n_sing_alpha = n_occ_alpha * n_vir_alpha;
103104
const auto n_doub_alpha = (n_sing_alpha * (n_sing_alpha - norb + 1)) / 4;
@@ -190,8 +191,8 @@ double asci_pt2_constraint(
190191
const auto& eps_beta = bcd.orb_ens_beta;
191192

192193
const auto state = det | beta;
193-
const auto state_alpha = alpha_string(state);
194-
const auto state_beta = beta_string(beta);
194+
const auto state_alpha = wfn_traits::alpha_string(state);
195+
const auto state_beta = wfn_traits::beta_string(beta);
195196
// BB Excitations
196197
append_singles_asci_contributions<Spin::Beta>(
197198
coeff, state, state_beta, occ_beta, vir_beta, occ_alpha,

include/macis/hamiltonian_generator/double_loop.hpp

Lines changed: 20 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ class DoubleLoopHamiltonianGenerator : public HamiltonianGenerator<WfnType> {
3131
sparse_matrix_type<index_t> make_csr_hamiltonian_block_(
3232
full_det_iterator bra_begin, full_det_iterator bra_end,
3333
full_det_iterator ket_begin, full_det_iterator ket_end, double H_thresh) {
34+
using wfn_traits = wavefunction_traits<WfnType>;
3435
const size_t nbra_dets = std::distance(bra_begin, bra_end);
3536
const size_t nket_dets = std::distance(ket_begin, ket_end);
3637

@@ -47,10 +48,10 @@ class DoubleLoopHamiltonianGenerator : public HamiltonianGenerator<WfnType> {
4748
const auto bra = *(bra_begin + i);
4849

4950
size_t nrow = 0;
50-
if(bra.count()) {
51+
if(wfn_traits::count(bra)) {
5152
// Separate out into alpha/beta components
52-
spin_det_t bra_alpha = alpha_string(bra);
53-
spin_det_t bra_beta = beta_string(bra);
53+
spin_det_t bra_alpha = wfn_traits::alpha_string(bra);
54+
spin_det_t bra_beta = wfn_traits::beta_string(bra);
5455

5556
// Get occupied indices
5657
bits_to_indices(bra_alpha, bra_occ_alpha);
@@ -59,14 +60,14 @@ class DoubleLoopHamiltonianGenerator : public HamiltonianGenerator<WfnType> {
5960
// Loop over ket determinants
6061
for(size_t j = 0; j < nket_dets; ++j) {
6162
const auto ket = *(ket_begin + j);
62-
if(ket.count()) {
63-
spin_det_t ket_alpha = alpha_string(ket);
64-
spin_det_t ket_beta = beta_string(ket);
63+
if(wfn_traits::count(ket)) {
64+
spin_det_t ket_alpha = wfn_traits::alpha_string(ket);
65+
spin_det_t ket_beta = wfn_traits::beta_string(ket);
6566

6667
full_det_t ex_total = bra ^ ket;
67-
if(ex_total.count() <= 4) {
68-
spin_det_t ex_alpha = alpha_string(ex_total);
69-
spin_det_t ex_beta = beta_string(ex_total);
68+
if(wfn_traits::count(ex_total) <= 4) {
69+
spin_det_t ex_alpha = wfn_traits::alpha_string(ex_total);
70+
spin_det_t ex_beta = wfn_traits::beta_string(ex_total);
7071

7172
// Compute Matrix Element
7273
const auto h_el = this->matrix_element(
@@ -117,6 +118,7 @@ class DoubleLoopHamiltonianGenerator : public HamiltonianGenerator<WfnType> {
117118
void form_rdms(full_det_iterator bra_begin, full_det_iterator bra_end,
118119
full_det_iterator ket_begin, full_det_iterator ket_end,
119120
double *C, matrix_span_t ordm, rank4_span_t trdm) override {
121+
using wfn_traits = wavefunction_traits<WfnType>;
120122
const size_t nbra_dets = std::distance(bra_begin, bra_end);
121123
const size_t nket_dets = std::distance(ket_begin, ket_end);
122124

@@ -126,10 +128,10 @@ class DoubleLoopHamiltonianGenerator : public HamiltonianGenerator<WfnType> {
126128
for(size_t i = 0; i < nbra_dets; ++i) {
127129
const auto bra = *(bra_begin + i);
128130
// if( (i%1000) == 0 ) std::cout << i << std::endl;
129-
if(bra.count()) {
131+
if(wfn_traits::count(bra)) {
130132
// Separate out into alpha/beta components
131-
spin_det_t bra_alpha = alpha_string(bra);
132-
spin_det_t bra_beta = beta_string(bra);
133+
spin_det_t bra_alpha = wfn_traits::alpha_string(bra);
134+
spin_det_t bra_beta = wfn_traits::beta_string(bra);
133135

134136
// Get occupied indices
135137
bits_to_indices(bra_alpha, bra_occ_alpha);
@@ -138,14 +140,14 @@ class DoubleLoopHamiltonianGenerator : public HamiltonianGenerator<WfnType> {
138140
// Loop over ket determinants
139141
for(size_t j = 0; j < nket_dets; ++j) {
140142
const auto ket = *(ket_begin + j);
141-
if(ket.count()) {
142-
spin_det_t ket_alpha = alpha_string(ket);
143-
spin_det_t ket_beta = beta_string(ket);
143+
if(wfn_traits::count(ket)) {
144+
spin_det_t ket_alpha = wfn_traits::alpha_string(ket);
145+
spin_det_t ket_beta = wfn_traits::beta_string(ket);
144146

145147
full_det_t ex_total = bra ^ ket;
146-
if(ex_total.count() <= 4) {
147-
spin_det_t ex_alpha = alpha_string(ex_total);
148-
spin_det_t ex_beta = beta_string(ex_total);
148+
if(wfn_traits::count(ex_total) <= 4) {
149+
spin_det_t ex_alpha = wfn_traits::alpha_string(ex_total);
150+
spin_det_t ex_beta = wfn_traits::beta_string(ex_total);
149151

150152
const double val = C[i] * C[j];
151153

include/macis/hamiltonian_generator/matrix_elements.hpp

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -14,10 +14,11 @@ namespace macis {
1414
template <typename WfnType>
1515
double HamiltonianGenerator<WfnType>::matrix_element(full_det_t bra,
1616
full_det_t ket) const {
17-
auto bra_alpha = alpha_string(bra);
18-
auto ket_alpha = alpha_string(ket);
19-
auto bra_beta = beta_string(bra);
20-
auto ket_beta = beta_string(ket);
17+
using wfn_traits = wavefunction_traits<WfnType>;
18+
auto bra_alpha = wfn_traits::alpha_string(bra);
19+
auto ket_alpha = wfn_traits::alpha_string(ket);
20+
auto bra_beta = wfn_traits::beta_string(bra);
21+
auto ket_beta = wfn_traits::beta_string(ket);
2122

2223
auto ex_alpha = bra_alpha ^ ket_alpha;
2324
auto ex_beta = bra_beta ^ ket_beta;
@@ -35,8 +36,9 @@ double HamiltonianGenerator<WfnType>::matrix_element(
3536
spin_det_t bra_beta, spin_det_t ket_beta, spin_det_t ex_beta,
3637
const std::vector<uint32_t>& bra_occ_alpha,
3738
const std::vector<uint32_t>& bra_occ_beta) const {
38-
const uint32_t ex_alpha_count = ex_alpha.count();
39-
const uint32_t ex_beta_count = ex_beta.count();
39+
using spin_wfn_traits = wavefunction_traits<spin_det_t>;
40+
const uint32_t ex_alpha_count = spin_wfn_traits::count(ex_alpha);
41+
const uint32_t ex_beta_count = spin_wfn_traits::count(ex_beta);
4042

4143
if((ex_alpha_count + ex_beta_count) > 4) return 0.;
4244

0 commit comments

Comments
 (0)