MADNESS  version 0.9
TDA_XC.h
Go to the documentation of this file.
1 /*
2  * tdhf_DFT.h
3  *
4  * Created on: Jun 30, 2014
5  * Author: kottmanj
6  */
7 
8 #ifndef TDHF_DFT_H_
9 #define TDHF_DFT_H_
10 
11 #include <chem/projector.h>
12 //#include <examples/mp2.h>
13 
14 // LIBXC
15 //#ifdef MADNESS_HAS_LIBXC
16 //#include <xc.h>
17 //#endif
18 
19 #include<examples/nonlinsol.h>
20 #include<chem/SCF.h>
21 #include <madness/mra/operator.h>
22 #include <madness/mra/mra.h>
23 #include <madness/mra/vmra.h>
24 #include <madness/mra/lbdeux.h>
25 #include <madness/misc/ran.h>
26 
27 #include </usr/include/math.h> /* pow */
28 
29 
30 
31 namespace madness{
32 
33 // Stolen from xc_functional helper structure of lib/chem/xcfunctional.h
36  : xc(&xc), what(what), ispin(ispin){}
37 
38  const XCfunctional* xc;
39  const int what;
40  const int ispin;
41 
42  madness::Tensor<double> operator()(const madness::Key<3> & key, const std::vector< madness::Tensor<double> >& t) const
43  {
44  MADNESS_ASSERT(xc);
45  madness::Tensor<double> r = xc->vxc(t, ispin, what);
46  return r;
47  }
48 };
49 
50 struct make_fxc{
51  make_fxc(const XCfunctional& xc, int ispin,int what)
52  : xc(&xc), what(what), ispin(ispin){}
53 
54  const XCfunctional* xc;
55  const int what;
56  const int ispin;
57 
58  madness::Tensor<double> operator()(const madness::Key<3> & key, const std::vector< madness::Tensor<double> >& t) const
59  {
60  MADNESS_ASSERT(xc);
61  madness::Tensor<double> r = xc->fxc(t, ispin, what);
62  return r;
63  }
64 };
65 
68  : xc(&xc), what(what), ispin(ispin){}
69 
70  const XCfunctional* xc;
71  const int what;
72  const int ispin;
73 
74  madness::Tensor<double> operator()(const madness::Key<3> & key, const std::vector< madness::Tensor<double> >& t) const
75  {
76  MADNESS_ASSERT(xc);
77  madness::Tensor<double> result;
78 
79  if(what == 0){
80  // gives back d2fdrho2
81  result=xc->fxc(t,ispin,0);
82  }
83  else if(what == 1){
84  // gives back d2fdrhodsigma
85  result=xc->fxc(t,ispin,1);
86  }
87  else if(what == 2){
88  // gives back d2fdsigma2
89  result=xc->fxc(t,ispin,2);
90  }
91  else MADNESS_EXCEPTION("what can only be in the range of 0-2",1);
92 
93  return result;
94  }
95 };
96 
99  : xc(&xc), what(what), ispin(ispin){}
100 
101  const XCfunctional* xc;
102  const int what;
103  const int ispin;
104 
105  madness::Tensor<double> operator()(const madness::Key<3> & key, const std::vector< madness::Tensor<double> >& t) const
106  {
107  MADNESS_ASSERT(xc);
108  // Make fxc kernel
109  madness::Tensor<double> result;
110  if(xc->is_lda()){
111  std::vector< madness::Tensor<double> > rho;
112  rho.push_back(t[0]);
113  madness::Tensor<double> fxc = xc->fxc(rho, ispin, 0);
114 
115 
116 
117  // multiply kernel with perturbed density (last element of t-vector)
118  fxc.emul(t.back());
119 
120  result = fxc;
121 
122  }
123  // For GGA the uncomming vector of tensors should contain:
124  // t[0] = unperturbed density
125  // t[1] = unperturbed sigma (gradient of rho * gradient of rho)
126  // t[2] = perturbed sigma (gradient of rho times gradient of rhoprime)
127  // t[3] = perturbed density (rhoprime)
128 
129  if(xc->is_gga()){
130  std::vector< madness::Tensor<double> > rho_and_sigma;
131 
132  madness::Tensor<double> d2fdrho2;
133  madness::Tensor<double> d2fdrhodsigma;
134  madness::Tensor<double> d2fdsigma2;
135  rho_and_sigma.push_back(t[0]);
136  rho_and_sigma.push_back(t[1]);
137 
138  if(what==0){
139  // Create the first term of yanais formula (13) for closed shells
140  // d2f/drho2*rhoprime + 2*d2f/drhodsigma*(grad_rho*grad_rhoprime)
141  d2fdrho2 = xc->fxc(rho_and_sigma,ispin,0);
142  d2fdrhodsigma = xc->fxc(rho_and_sigma,ispin,1);
143 
144  result = d2fdrho2;
145  result.emul(t[3]);
146  d2fdrhodsigma.emul(t[2]);
147  result.gaxpy(1.0,d2fdrhodsigma,2.0);
148 
149  }
150  else if(what==1){
151  // Create part of the second term of yanais formula (13) for closed shell
152  // 2*d2fdrhodsigma * rhoprime + 4*d2fdisgma2(grad_rho*grad_rhoprime);
153  // This has to be multiplied with grad_rho and the divergence should be taken afterwards
154  d2fdrhodsigma = xc->fxc(rho_and_sigma,ispin,1);
155  d2fdsigma2 = xc->fxc(rho_and_sigma,ispin,2);
156 
157  result = d2fdrhodsigma;
158  result.emul(t[3]);
159  d2fdsigma2.emul(t[2]);
160  result.gaxpy(2.0,d2fdsigma2,4.0);
161 
162  }
163  else if(what==2){
164  // Create the last part of yanais formula (13) for closed shell
165  // df/dsigma
166  // This has to be multiplied with 2, contracted with grad_rhoprime and the divergence taken afterwards
167  result = xc->vxc(rho_and_sigma,ispin,1);
168 
169  }
170  else MADNESS_EXCEPTION("What parameter of convolute_with_kernel was not from 0-2",1);
171 
172 
173 
174  }
175  return result;
176  }
177 };
178 
180  apply_kernel_functor(const XCfunctional & xc, int ispin, int what): xc(&xc),what(what),ispin(ispin){}
181  const XCfunctional * xc;
182  const int what;
183  const int ispin;
184 
185  madness::Tensor<double> operator()(const madness::Key<3> & key, const std::vector<madness::Tensor<double> >& t)const
186  {
187  MADNESS_ASSERT(xc);
188  // Make fxc kernel with rho_ (first entry of t)
189  std::vector<madness::Tensor<double> > rho;
190  rho.push_back(t[0]);
191  if(xc->is_gga()) rho.push_back(t[1]);
192  madness::Tensor<double> fxc = xc->fxc(rho, ispin, what);
193  // multiply the kernel with the density and the active mo (product is the last entry of t)
194  fxc.emul(t[1]);
195  fxc.emul(t[2]);
196  return fxc;
197  }
198 };
199 
200 
201 class TDA_DFT {
202 
203 public:
204  TDA_DFT(World &world,const SCF &calc): world(world),calc(calc), xcfunctional_(calc.xc){
205 
206  // Potential check
207  std::cout << "Used Potential:\n";
208  std::cout << "lda: " << xcfunctional_.is_lda();
209  std::cout << "gga: " << xcfunctional_.is_gga();
210  std::cout << " spin polarized: " << xcfunctional_.is_spin_polarized() << std::endl;
211 
212  // Make unperturbed Density and unperturbed xc-potential
213  // The density for spin unrestricted and closed shell is arho (without factor 2, because this is added in the XCfunctional class automatically)
214  real_function_3d rho = real_factory_3d(world);
215  for(size_t i=0;i<calc.amo.size();i++){
216  rho +=calc.amo[i]*calc.amo[i];
217  }
218  rho_=rho;
219 
220  // Make the contracted gradient of the unperturbed density sum_i (d/dxi rho)^2
221  if(xcfunctional_.is_gga()){
222  vecfuncT delrho;
223  std::vector< std::shared_ptr<real_derivative_3d> > gradop;
224  gradop =gradient_operator<double,3>(world);
225  rho.reconstruct();
226  for (int axis = 0; axis < 3; ++axis){
227  delrho.push_back((*gradop[axis])(rho, false)); // delrho
228  }
229  world.gop.fence(); // NECESSARY
230 
231  sigma_= delrho[0] * delrho[0] + delrho[1] * delrho[1]+ delrho[2] * delrho[2]; // sigma_aa
232  }
233 
234  vxc_=make_unperturbed_vxc(rho_);
235 
236  //DEBUG
237  plot_plane(world,vxc_,"debug_pvxc");
238  double exc = 0.5*inner(vxc_,rho_);
239  std::cout << "unperturbed exchange correlation energy : " << exc << " density norm: " << rho_.norm2() << " vxc norm : " << vxc_.norm2()<< std::endl;
240  //DEBUG END
241  }
243  TDA_DFT(const TDA_DFT &other);
244 
245 
248 
249  void print_information();
251  real_function_3d get_perturbed_potential(const real_function_3d &perturbed_density){return V(perturbed_density);}
253  vecfuncT apply_kernel(const vecfuncT &x)const;
255  XCfunctional get_xcfunctional()const{return xcfunctional_;}
256  real_function_3d calculate_unperturbed_vxc(const real_function_3d &rho)const{return make_unperturbed_vxc(rho);}
257  vecfuncT get_lda_intermediate(vecfuncT & mos)const{return multiply_with_kernel(mos);}
258  // Test which type of functional is used
259  bool is_gga()const{
260  return xcfunctional_.is_gga();
261  }
262 
263 private:
266  const SCF &calc;
267 
269  const XCfunctional &xcfunctional_;
271  real_function_3d rho_;
273  real_function_3d sigma_;
275  real_function_3d vxc_;
277  real_function_3d fxc_;
279  real_function_3d vx_dirac(const real_function_3d &perturbed_density);
280  real_function_3d V(const real_function_3d &perturbed_density);
281  real_function_3d make_unperturbed_vxc(const real_function_3d &rho)const;
282  real_function_3d make_lda_kernel(const real_function_3d &rho)const;
283  vecfuncT multiply_with_kernel(vecfuncT &active_mo)const;
284 
285 
286 
287 };
288 
289 } // madness namesapce
290 #endif /* TDHF_DFT_H_ */
WorldGopInterface & gop
Global operations.
Definition: worldfwd.h:462
const int what
Definition: TDA_XC.h:102
madness::Tensor< double > operator()(const madness::Key< 3 > &key, const std::vector< madness::Tensor< double > > &t) const
Definition: TDA_XC.h:58
real_function_3d get_unperturbed_vxc() const
Definition: TDA_XC.h:254
Main include file for MADNESS and defines Function interface.
const int ispin
Definition: TDA_XC.h:56
madness::Tensor< double > operator()(const madness::Key< 3 > &key, const std::vector< madness::Tensor< double > > &t) const
Definition: TDA_XC.h:105
const XCfunctional * xc
Definition: TDA_XC.h:38
const XCfunctional * xc
Definition: TDA_XC.h:54
bool is_lda() const
Returns true if the potential is lda.
Definition: chem/xcfunctional_ldaonly.cc:57
unperturbed_vxc(const XCfunctional &xc, int ispin, int what)
Definition: TDA_XC.h:35
Definition: chem/SCF.h:712
vecfuncT apply_kernel(const vecfuncT &x) const
Definition: TDA_XC.cc:157
XCfunctional xc
Definition: hedft.cc:54
const int what
Definition: TDA_XC.h:55
const int ispin
Definition: TDA_XC.h:72
Definition: TDA_XC.h:50
make_fxc(const XCfunctional &xc, int ispin, int what)
Definition: TDA_XC.h:51
void plot_plane(World &world, const Function< double, NDIM > &function, const std::string name)
Definition: funcplot.h:531
const int what
Definition: TDA_XC.h:39
T inner(const vecfunc< T, NDIM > &a, const vecfunc< T, NDIM > &b)
the non-linear solver requires an inner product
Definition: nemo.h:112
madness::Tensor< double > operator()(const madness::Key< 3 > &key, const std::vector< madness::Tensor< double > > &t) const
Definition: TDA_XC.h:74
vecfuncT amo
alpha and beta molecular orbitals
Definition: chem/SCF.h:729
const int what
Definition: TDA_XC.h:182
Implements most functionality of separated operators.
bool is_gga() const
Definition: TDA_XC.h:259
double norm2() const
Returns the 2-norm of the function ... global sum ... works in either basis.
Definition: mra.h:650
Defines operations on vectors of FunctionsThis file defines a number of operations on vectors of func...
const int ispin
Definition: TDA_XC.h:103
void reconstruct(bool fence=true) const
Reconstructs the function, transforming into scaling function basis. Possible non-blocking comm...
Definition: mra.h:737
Example implementation of Krylov-subspace nonlinear equation solver.
madness::Tensor< double > operator()(const madness::Key< 3 > &key, const std::vector< madness::Tensor< double > > &t) const
Definition: TDA_XC.h:185
vector< functionT > vecfuncT
Definition: chem/corepotential.cc:61
std::vector< std::shared_ptr< real_derivative_3d > > gradop
Definition: h2dft.cc:52
vecfuncT get_lda_intermediate(vecfuncT &mos) const
Definition: TDA_XC.h:257
World & world
The world.
Definition: TDA_XC.h:247
A parallel world with full functionality wrapping an MPI communicator.
Definition: worldfwd.h:416
void fence()
Synchronizes all processes in communicator AND globally ensures no pending AM or tasks.
Definition: worldgop.cc:52
const XCfunctional * xc
Definition: TDA_XC.h:70
Definition: TDA_XC.h:34
madness::Tensor< double > fxc(const std::vector< madness::Tensor< double > > &t, const int ispin, const int what) const
Definition: chem/xcfunctional_ldaonly.cc:150
XCfunctional get_xcfunctional() const
Definition: TDA_XC.h:255
madness::Tensor< double > operator()(const madness::Key< 3 > &key, const std::vector< madness::Tensor< double > > &t) const
Definition: TDA_XC.h:42
madness::Tensor< double > vxc(const std::vector< madness::Tensor< double > > &t, const int ispin, const int what) const
Computes components of the potential (derivative of the energy functional) at np points.
Definition: chem/xcfunctional_ldaonly.cc:115
TDA_DFT(World &world, const SCF &calc)
Definition: TDA_XC.h:204
perturbed_vxc(const XCfunctional &xc, int ispin, int what)
Definition: TDA_XC.h:98
real_function_3d get_perturbed_potential(const real_function_3d &perturbed_density)
Definition: TDA_XC.h:251
const XCfunctional * xc
Definition: TDA_XC.h:181
Definition: TDA_XC.h:179
get_derivatives(const XCfunctional &xc, int ispin, int what)
Definition: TDA_XC.h:67
const XCfunctional * xc
Definition: TDA_XC.h:101
Implements (2nd generation) static load/data balancing for functions.
Definition: TDA_XC.h:201
const int what
Definition: TDA_XC.h:71
const int ispin
Definition: TDA_XC.h:183
FunctionFactory< double, 3 > real_factory_3d
Definition: functypedefs.h:93
Definition: TDA_XC.h:97
const int ispin
Definition: TDA_XC.h:40
#define MADNESS_EXCEPTION(msg, value)
Definition: worldexc.h:88
apply_kernel_functor(const XCfunctional &xc, int ispin, int what)
Definition: TDA_XC.h:180
Definition: TDA_XC.h:66
bool is_gga() const
Returns true if the potential is gga (needs first derivatives)
Definition: chem/xcfunctional_ldaonly.cc:61
real_function_3d convolution_with_kernel(real_function_3d &perturbed_density) const
Definition: TDA_XC.cc:32
Simplified interface to XC functionals.
Definition: chem/xcfunctional.h:41
Holds machinery to set up Functions/FuncImpls using various Factories and Interfaces.
Definition: chem/atomutil.cc:45
vecfuncT evaluate_derivatives() const
Definition: TDA_XC.cc:17
Key is the index for a node of the 2^NDIM-tree.
Definition: key.h:69
real_function_3d calculate_unperturbed_vxc(const real_function_3d &rho) const
Definition: TDA_XC.h:256
void print_information()
bool is_spin_polarized() const
Returns true if the functional is spin_polarized.
Definition: chem/xcfunctional.h:156