32 template<
typename DU_TYPE>
41 matrix_inverter_kind_(matrix_inverter_kind)
51 std::ostringstream err_msg;
52 err_msg <<
"The SPOSet " <<
Phi->getName() <<
" only has " <<
Phi->getOrbitalSetSize() <<
" orbitals " 53 <<
"but this determinant needs at least " <<
NumPtcls << std::endl;
54 throw std::runtime_error(err_msg.str());
58 template<
typename DU_TYPE>
65 int failure_counter = 0;
70 updateEng.invert_transpose(logdetT, invMat, log_value_);
71 if (failure_counter > 0)
73 std::ostringstream success_msg;
74 success_msg <<
"Successful rerun matrix inversion on Rank " <<
OHMMS::Controller->
rank() <<
" Thread " 76 std::cerr << success_msg.str();
80 catch (
const std::exception&
e)
83 std::ostringstream err_msg;
84 err_msg << failure_counter <<
"th matrix inversion on Rank " <<
OHMMS::Controller->
rank() <<
" Thread " 85 <<
omp_get_thread_num() <<
" which failed earlier with an error:\n " <<
e.what() << std::endl;
86 std::cerr << err_msg.str();
87 if (failure_counter == 1)
90 std::ostringstream matfname;
92 std::ofstream matfile(matfname.str().c_str(), std::ios::app);
93 matfile << std::setprecision(14) << std::scientific;
94 for (
size_t i = 0; i < logdetT.rows(); i++)
96 for (
size_t j = 0; j < logdetT.cols(); j++)
97 matfile <<
" " << logdetT[i][j];
102 }
while (!success && failure_counter < 5);
104 throw std::runtime_error(
"Matrix inversion failed after " + std::to_string(failure_counter) +
" attempts.\n");
108 host_inverter_.invert_transpose(logdetT, invMat, log_value_);
109 updateEng.initializeInv(psiM);
115 template<
typename DU_TYPE>
118 if (Bytes_in_WFBuffer > 0)
119 throw std::runtime_error(
"DiracDeterimnant just went out of sync with buffer");
123 updateEng.resize(norb, ndelay_);
124 psiM.resize(nel, norb);
125 dpsiM.resize(nel, norb);
126 d2psiM.resize(nel, norb);
129 psiM_temp.resize(nel, norb);
131 dpsiV.resize(NumOrbitals);
132 dspin_psiV.resize(NumOrbitals);
133 d2psiV.resize(NumOrbitals);
134 FirstAddressOfdV = &(dpsiM(0, 0)[0]);
135 LastAddressOfdV = FirstAddressOfdV + NumPtcls * NumOrbitals *
DIM;
138 template<
typename DU_TYPE>
142 const int WorkingIndex = iat - FirstIndex;
143 assert(WorkingIndex >= 0);
144 invRow_id = WorkingIndex;
145 updateEng.getInvRow(psiM, WorkingIndex, invRow);
151 template<
typename DU_TYPE>
156 Phi->evaluate_spin(P, iat, psiV, dspin_psiV);
158 const int WorkingIndex = iat - FirstIndex;
159 assert(WorkingIndex >= 0);
160 invRow_id = WorkingIndex;
161 updateEng.getInvRow(psiM, WorkingIndex, invRow);
169 template<
typename DU_TYPE>
176 Phi->evaluateVGL(P, iat, psiV, dpsiV, d2psiV);
178 return ratioGrad_compute(iat, grad_iat);
181 template<
typename DU_TYPE>
186 UpdateMode = ORB_PBYP_PARTIAL;
187 const int WorkingIndex = iat - FirstIndex;
188 assert(WorkingIndex >= 0);
193 if (invRow_id != WorkingIndex)
195 invRow_id = WorkingIndex;
196 updateEng.getInvRow(psiM, WorkingIndex, invRow);
198 curRatio =
simd::dot(invRow.data(), psiV.data(), invRow.size());
200 simd::dot(invRow.data(), dpsiV.data(), invRow.size());
204 template<
typename DU_TYPE>
212 Phi->evaluateVGL_spin(P, iat, psiV, dpsiV, d2psiV, dspin_psiV);
217 UpdateMode = ORB_PBYP_PARTIAL;
218 const int WorkingIndex = iat - FirstIndex;
219 assert(WorkingIndex >= 0);
223 if (invRow_id != WorkingIndex)
225 invRow_id = WorkingIndex;
226 updateEng.getInvRow(psiM, WorkingIndex, invRow);
228 curRatio =
simd::dot(invRow.data(), psiV.data(), invRow.size());
230 simd::dot(invRow.data(), dpsiV.data(), invRow.size());
233 simd::dot(invRow.data(), dspin_psiV.data(), invRow.size());
239 template<
typename DU_TYPE>
243 std::vector<PsiValue>& ratios,
244 std::vector<GradType>& grad_new)
const 249 phi_list.reserve(wfc_list.size());
251 psi_v_list.reserve(wfc_list.size());
253 dpsi_v_list.reserve(wfc_list.size());
255 d2psi_v_list.reserve(wfc_list.size());
260 phi_list.push_back(*
det.Phi);
261 psi_v_list.push_back(
det.psiV);
262 dpsi_v_list.push_back(
det.dpsiV);
263 d2psi_v_list.push_back(
det.d2psiV);
266 Phi->mw_evaluateVGL(phi_list, p_list, iat, psi_v_list, dpsi_v_list, d2psi_v_list);
269 for (
int iw = 0; iw < wfc_list.size(); iw++)
276 template<
typename DU_TYPE>
281 std::ostringstream msg;
282 msg <<
"DiracDeterminant::acceptMove curRatio is " << curRatio <<
"! Report a bug." << std::endl;
283 throw std::runtime_error(msg.str());
286 const int WorkingIndex = iat - FirstIndex;
287 assert(WorkingIndex >= 0);
289 updateEng.acceptRow(psiM, WorkingIndex, psiV, curRatio);
291 updateEng.updateInvMat(psiM);
294 if (UpdateMode == ORB_PBYP_PARTIAL)
296 simd::copy(dpsiM[WorkingIndex], dpsiV.data(), NumOrbitals);
297 simd::copy(d2psiM[WorkingIndex], d2psiV.data(), NumOrbitals);
304 template<
typename DU_TYPE>
310 template<
typename DU_TYPE>
316 updateEng.updateInvMat(psiM);
319 template<
typename DU_TYPE>
324 if (UpdateMode == ORB_PBYP_RATIO)
327 Phi->evaluate_notranspose(P, FirstIndex, LastIndex, psiM_temp, dpsiM, d2psiM);
328 UpdateMode = ORB_WALKER;
331 for (
size_t i = 0, iat = FirstIndex; i < NumPtcls; ++i, ++iat)
336 L[iat] += dot_temp -
dot(rv, rv);
340 template<
typename DU_TYPE>
343 if (Bytes_in_WFBuffer == 0)
346 Bytes_in_WFBuffer = buf.
current();
347 buf.
add(psiM.first_address(), psiM.last_address());
348 buf.
add(FirstAddressOfdV, LastAddressOfdV);
349 buf.
add(d2psiM.first_address(), d2psiM.last_address());
350 Bytes_in_WFBuffer = buf.
current() - Bytes_in_WFBuffer;
358 buf.
forward(Bytes_in_WFBuffer);
369 template<
typename DU_TYPE>
376 evaluateLog(P, G, L);
378 updateAfterSweep(P, G, L);
382 template<
typename DU_TYPE>
387 evaluateGL(P, P.
G, P.
L, fromscratch);
390 buf.
forward(Bytes_in_WFBuffer);
396 template<
typename DU_TYPE>
406 updateEng.initializeInv(psiM);
409 template<
typename DU_TYPE>
419 template<
typename DU_TYPE>
422 UpdateMode = ORB_PBYP_RATIO;
423 const int WorkingIndex = iat - FirstIndex;
424 assert(WorkingIndex >= 0);
427 Phi->evaluateValue(P, iat, psiV);
434 if (invRow_id != WorkingIndex)
436 invRow_id = WorkingIndex;
437 updateEng.getInvRow(psiM, WorkingIndex, invRow);
439 curRatio =
simd::dot(invRow.data(), psiV.data(), invRow.size());
444 template<
typename DU_TYPE>
449 const int WorkingIndex = VP.
refPtcl - FirstIndex;
450 assert(WorkingIndex >= 0);
451 std::copy_n(psiM[WorkingIndex], invRow.size(), invRow.data());
455 Phi->evaluateDetRatios(VP, psiV, invRow, ratios);
459 template<
typename DU_TYPE>
464 const int WorkingIndex = VP.
refPtcl - FirstIndex;
465 assert(WorkingIndex >= 0);
466 std::copy_n(psiM[WorkingIndex], invRow.size(), invRow.data());
470 Phi->evaluateDetSpinorRatios(VP, psiV, spinor_multiplier, invRow, ratios);
474 template<
typename DU_TYPE>
477 std::vector<std::vector<ValueType>>& ratios)
const 479 const size_t nw = wfc_list.size();
483 std::vector<const ValueType*> invRow_ptr_list;
484 phi_list.reserve(nw);
485 psiV_list.reserve(nw);
486 invRow_ptr_list.reserve(nw);
490 for (
size_t iw = 0; iw < nw; iw++)
494 const int WorkingIndex = vp.refPtcl - FirstIndex;
495 assert(WorkingIndex >= 0);
500 phi_list.push_back(*
det.Phi);
501 psiV_list.push_back(
det.psiV);
502 invRow_ptr_list.push_back(
det.psiM[WorkingIndex]);
510 if (Phi->isOMPoffload())
511 for (
int iw = 0; iw < phi_list.size(); iw++)
513 Vector<ValueType> invRow(const_cast<ValueType*>(invRow_ptr_list[iw]), psiV_list[iw].
get().size());
514 phi_list[iw].evaluateDetRatios(vp_list[iw], psiV_list[iw], invRow, ratios[iw]);
517 Phi->mw_evaluateDetRatios(phi_list, vp_list, psiV_list, invRow_ptr_list, ratios);
521 template<
typename DU_TYPE>
524 std::vector<ValueType>& ratios,
527 const int WorkingIndex = VP.
refPtcl - FirstIndex;
528 assert(WorkingIndex >= 0);
529 std::copy_n(psiM[WorkingIndex], invRow.size(), invRow.data());
530 Phi->evaluateDerivRatios(VP, optvars, psiV, invRow, ratios, dratios, FirstIndex, LastIndex);
533 template<
typename DU_TYPE>
537 Phi->evaluateValue(P, -1, psiV);
543 template<
typename DU_TYPE>
546 grad_source_psiM.resize(NumPtcls, NumOrbitals);
547 grad_lapl_source_psiM.resize(NumPtcls, NumOrbitals);
548 grad_grad_source_psiM.resize(NumPtcls, NumOrbitals);
549 phi_alpha_Minv.resize(NumPtcls, NumOrbitals);
550 grad_phi_Minv.resize(NumPtcls, NumOrbitals);
551 lapl_phi_Minv.resize(NumPtcls, NumOrbitals);
552 grad_phi_alpha_Minv.resize(NumPtcls, NumOrbitals);
555 template<
typename DU_TYPE>
561 if (Phi->hasIonDerivs())
563 resizeScratchObjectsForIonDerivs();
564 Phi->evaluateGradSource(P, FirstIndex, LastIndex, source, iat, grad_source_psiM);
565 g =
simd::dot(psiM.data(), grad_source_psiM.data(), psiM.size());
571 template<
typename DU_TYPE>
575 grad_grad_source_psiM.resize(psiM.rows(), psiM.cols());
577 Phi->evaluate_notranspose(P, FirstIndex, LastIndex, psiM_temp, dpsiM, grad_grad_source_psiM);
578 invertPsiM(psiM_temp, psiM);
580 phi_alpha_Minv = 0.0;
583 grad_phi_alpha_Minv = 0.0;
586 for (
int i = 0, iat = FirstIndex; i < NumPtcls; i++, iat++)
592 hess_tmp =
simd::dot(psiM[i], grad_grad_source_psiM[i], NumOrbitals);
597 template<
typename DU_TYPE>
606 if (Phi->hasIonDerivs())
608 resizeScratchObjectsForIonDerivs();
609 Phi->evaluateGradSource(P, FirstIndex, LastIndex, source, iat, grad_source_psiM, grad_grad_source_psiM,
610 grad_lapl_source_psiM);
631 phi_alpha_Minv = 0.0;
634 grad_phi_alpha_Minv = 0.0;
635 for (
int i = 0; i < NumPtcls; i++)
636 for (
int j = 0; j < NumOrbitals; j++)
638 lapl_phi_Minv(i, j) = 0.0;
639 for (
int k = 0; k < NumOrbitals; k++)
640 lapl_phi_Minv(i, j) += d2psiM(i, k) * psiM(j, k);
642 for (
int dim = 0; dim <
OHMMS_DIM; dim++)
644 for (
int i = 0; i < NumPtcls; i++)
645 for (
int j = 0; j < NumOrbitals; j++)
647 for (
int k = 0; k < NumOrbitals; k++)
649 phi_alpha_Minv(i, j)[dim] += grad_source_psiM(i, k)[dim] * psiM(j, k);
650 grad_phi_Minv(i, j)[dim] += dpsiM(i, k)[dim] * psiM(j, k);
651 for (
int dim_el = 0; dim_el <
OHMMS_DIM; dim_el++)
652 grad_phi_alpha_Minv(i, j)(dim, dim_el) += grad_grad_source_psiM(i, k)(dim, dim_el) * psiM(j, k);
656 for (
int i = 0, iel = FirstIndex; i < NumPtcls; i++, iel++)
660 for (
int dim = 0; dim <
OHMMS_DIM; dim++)
661 for (
int dim_el = 0; dim_el <
OHMMS_DIM; dim_el++)
662 dval(dim, dim_el) = grad_phi_alpha_Minv(i, i)(dim, dim_el);
663 for (
int j = 0; j < NumOrbitals; j++)
665 gradPsi += grad_source_psiM(i, j) * psiM(i, j);
666 for (
int dim = 0; dim <
OHMMS_DIM; dim++)
668 dval(dim, k) -= phi_alpha_Minv(j, i)[dim] * grad_phi_Minv(i, j)[k];
670 for (
int dim = 0; dim <
OHMMS_DIM; dim++)
673 grad_grad[dim][iel][k] += dval(dim, k);
674 for (
int j = 0; j < NumOrbitals; j++)
677 lapl_grad[dim][iel] += grad_lapl_source_psiM(i, j)[dim] * psiM(i, j);
680 for (
int dim_el = 0; dim_el <
OHMMS_DIM; dim_el++)
681 lapl_grad[dim][iel] -=
682 (
RealType)2.0 * grad_phi_alpha_Minv(j, i)(dim, dim_el) * grad_phi_Minv(i, j)[dim_el];
685 lapl_grad[dim][iel] -= phi_alpha_Minv(j, i)[dim] * lapl_phi_Minv(i, j);
687 for (
int dim_el = 0; dim_el <
OHMMS_DIM; dim_el++)
688 lapl_grad[dim][iel] +=
689 (
RealType)2.0 * phi_alpha_Minv(j, i)[dim] * grad_phi_Minv(i, i)[dim_el] * grad_phi_Minv(i, j)[dim_el];
708 template<
typename DU_TYPE>
715 for (
int i = 0, iat = FirstIndex; i < NumPtcls; i++, iat++)
720 L[iat] += lap -
dot(rv, rv);
725 template<
typename DU_TYPE>
730 UpdateMode = ORB_WALKER;
731 Phi->evaluate_notranspose(P, FirstIndex, LastIndex, psiM_temp, dpsiM, d2psiM);
734 invertPsiM(psiM_temp, psiM);
740 template<
typename DU_TYPE>
746 Phi->evaluateDerivatives(P, active, dlogpsi, dhpsioverpsi, FirstIndex, LastIndex);
749 template<
typename DU_TYPE>
754 Phi->evaluateDerivativesWF(P, active, dlogpsi, FirstIndex, LastIndex);
757 template<
typename DU_TYPE>
760 return std::make_unique<DiracDeterminant<DU_TYPE>>(std::move(spo), FirstIndex, LastIndex, ndelay_,
761 matrix_inverter_kind_);
764 template<
typename DU_TYPE>
767 Phi->createResource(collection);
770 template<
typename DU_TYPE>
779 phi_list.push_back(*
det.Phi);
781 wfc_leader.
Phi->acquireResource(collection, phi_list);
784 template<
typename DU_TYPE>
793 phi_list.push_back(*
det.Phi);
795 wfc_leader.
Phi->releaseResource(collection, phi_list);
799 #if defined(ENABLE_CUDA) 802 #if defined(ENABLE_SYCL) void mw_evaluateRatios(const RefVectorWithLeader< WaveFunctionComponent > &wfc_list, const RefVectorWithLeader< const VirtualParticleSet > &vp_list, std::vector< std::vector< ValueType >> &ratios) const override
evaluate ratios to evaluate the non-local PP multiple walkers
void acquireResource(ResourceCollection &collection, const RefVectorWithLeader< WaveFunctionComponent > &wf_list) const override
acquire a shared resource from a collection
void recompute(const ParticleSet &P) override
recompute the value of the WaveFunctionComponents which require critical accuracy.
WaveFunctionComponent::PsiValue PsiValue
helper functions for EinsplineSetBuilder
int rank() const
return the rank
Tensor< T, D >::Type_t det(const Tensor< T, D > &a)
void resizeScratchObjectsForIonDerivs()
Resize all temporary arrays required for force computation.
T dot(const T *restrict a, const T *restrict b, int n, TRES res=TRES())
dot product
void acceptMove(ParticleSet &P, int iat, bool safe_to_delay=false) override
move was accepted, update the real container
QTBase::RealType RealType
void forward(size_type n)
void evaluateSpinorRatios(const VirtualParticleSet &VP, const std::pair< ValueVector, ValueVector > &spinor_multipler, std::vector< ValueType > &ratios) override
Used by SOECPComponent for faster SOC evaluation.
void resize(int nel, int morb)
reset the size: with the number of particles and number of orbtials
DetMatInvertor
determinant matrix inverter select
A ParticleSet that handles virtual moves of a selected particle of a given physical ParticleSet Virtu...
LogValue evaluateGL(const ParticleSet &P, ParticleSet::ParticleGradient &G, ParticleSet::ParticleLaplacian &L, bool fromscratch) override
compute gradients and laplacian of the TWF with respect to each particle.
void evaluateDerivativesWF(ParticleSet &P, const opt_variables_type &optvars, Vector< ValueType > &dlogpsi) override
Compute the derivatives of the log of the wavefunction with respect to optimizable parameters...
GradType evalGradWithSpin(ParticleSet &P, int iat, ComplexType &spingrad) final
return the current spin gradient for the iat-th particle Default implementation assumes that WaveFunc...
int refPtcl
Reference particle.
PsiValue ratioGrad(ParticleSet &P, int iat, GradType &grad_iat) override
evaluate the ratio of the new to old WaveFunctionComponent value and the new gradient ...
QTBase::ComplexType ComplexType
LogValue evaluateLog(const ParticleSet &P, ParticleSet::ParticleGradient &G, ParticleSet::ParticleLaplacian &L) override
evaluate log of a determinant for a particle set
void copyFromBuffer(ParticleSet &P, WFBufferType &buf) override
For particle-by-particle move.
void mw_ratioGrad(const RefVectorWithLeader< WaveFunctionComponent > &wfc_list, const RefVectorWithLeader< ParticleSet > &p_list, int iat, std::vector< PsiValue > &ratios, std::vector< GradType > &grad_new) const override
compute the ratio of the new to old WaveFunctionComponent value and the new gradient of multiple walk...
void copy(T1 *restrict target, const T2 *restrict source, size_t n)
copy function using memcpy
Attaches a unit to a Vector for IO.
std::complex< T > convertValueToLog(const std::complex< T > &logpsi)
evaluate log(psi) as log(|psi|) and phase
Communicate * Controller
Global Communicator for a process.
ParticleLaplacian L
laplacians of the particles
TWFFastDerivWrapper is a wrapper class for TrialWavefunction that provides separate and low level acc...
OrbitalSetTraits< ValueType >::HessType HessType
GradType evalGrad(ParticleSet &P, int iat) override
return the current gradient for the iat-th particle
SPOSet::ValueMatrix ValueMatrix
DiracDeterminant(std::unique_ptr< SPOSet > &&spos, int first, int last, int ndelay=1, DetMatInvertor matrix_inverter_kind=DetMatInvertor::ACCEL)
constructor
std::complex< QTFull::RealType > LogValue
void buildOptVariables(size_t nel)
An abstract class for a component of a many-body trial wave function.
omp_int_t omp_get_thread_num()
Specialized paritlce class for atomistic simulations.
void evaluateRatiosAlltoOne(ParticleSet &P, std::vector< ValueType > &ratios) override
evaluate the ratios of one virtual move with respect to all the particles
const std::unique_ptr< SPOSet > Phi
a set of single-particle orbitals used to fill in the values of the matrix
void createResource(ResourceCollection &collection) const override
initialize a shared resource and hand it to a collection
void completeUpdates() override
complete all the delayed or asynchronous operations before leaving the p-by-p move region...
void product(const Matrix< T > &A, const Matrix< T > &B, Matrix< T > &C)
static function to perform C=AB for real matrices
void evaluateDerivRatios(const VirtualParticleSet &VP, const opt_variables_type &optvars, std::vector< ValueType > &ratios, Matrix< ValueType > &dratios) override
evaluate ratios to evaluate the non-local PP
void updateAfterSweep(const ParticleSet &P, ParticleSet::ParticleGradient &G, ParticleSet::ParticleLaplacian &L)
void restore(int iat) override
move was rejected.
Tensor< typename BinaryReturn< T1, T2, OpMultiply >::Type_t, D > outerProduct(const TinyVector< T1, D > &lhs, const TinyVector< T2, D > &rhs)
void evaluateRatios(const VirtualParticleSet &VP, std::vector< ValueType > &ratios) override
compute multiple ratios for a particle move
SPOSet::HessVector HessVector
void releaseResource(ResourceCollection &collection, const RefVectorWithLeader< WaveFunctionComponent > &wf_list) const override
return a shared resource to a collection
ParticleGradient G
gradients of the particles
CASTTYPE & getCastedElement(size_t i) const
class to handle a set of variables that can be modified during optimizations
PsiValue ratioGrad_compute(int iat, GradType &grad_iat)
internal function computing ratio and gradients after computing the SPOs, used by ratioGrad...
QTFull::ValueType PsiValue
LogValue updateBuffer(ParticleSet &P, WFBufferType &buf, bool fromscratch=false) override
For particle-by-particle move.
PsiValue ratioGradWithSpin(ParticleSet &P, int iat, GradType &grad_iat, ComplexType &spingrad) final
evaluate the ratio of the new to old WaveFunctionComponent value and the new spin gradient Default im...
size_type current() const
std::vector< std::reference_wrapper< T > > RefVector
void registerData(ParticleSet &P, WFBufferType &buf) override
For particle-by-particle move.
CASTTYPE & getCastedLeader() const
void evaluateDerivatives(ParticleSet &P, const opt_variables_type &active, Vector< ValueType > &dlogpsi, Vector< ValueType > &dhpsioverpsi) override
Compute the derivatives of both the log of the wavefunction and kinetic energy with respect to optimi...
sycl::event copy_n(sycl::queue &aq, const T1 *restrict VA, size_t array_size, T2 *restrict VC, const std::vector< sycl::event > &events)
void registerTWFFastDerivWrapper(const ParticleSet &P, TWFFastDerivWrapper &twf) const final
Finds the SPOSet associated with this determinant, and registers it with WFN wrapper.
void invertPsiM(const ValueMatrix &logdetT, ValueMatrix &invMat)
invert psiM or its copies
Tensor< typename BinaryReturn< T1, T2, OpMultiply >::Type_t, D > dot(const AntiSymTensor< T1, D > &lhs, const AntiSymTensor< T2, D > &rhs)
LatticeGaussianProduct::ValueType ValueType
Declaration of DiracDeterminant with a S(ingle)P(article)O(rbital)Set.
const int NumPtcls
number of particles which belong to this Dirac determinant
QMCTraits::QTFull::ValueType mValueType
PsiValue ratio(ParticleSet &P, int iat) override
return the ratio only for the iat-th partcle move
T1 * lendReference(size_type n)
void put(std::complex< T1 > &x)
std::unique_ptr< DiracDeterminantBase > makeCopy(std::unique_ptr< SPOSet > &&spo) const override
cloning function
GradType evalGradSource(ParticleSet &P, ParticleSet &source, int iat) override
return the logarithmic gradient for the iat-th particle of the source particleset ...
void evaluateHessian(ParticleSet &P, HessVector &grad_grad_psi) override
int getGroupID(int iat) const
return the group id of a given particle in the particle set.
void add(std::complex< T1 > &x)
void get(std::complex< T1 > &x)