HPhi++  3.1.0
Multiply.cpp
Go to the documentation of this file.
1 /* HPhi - Quantum Lattice Model Simulator */
2 /* Copyright (C) 2015 The University of Tokyo */
3 
4 /* This program is free software: you can redistribute it and/or modify */
5 /* it under the terms of the GNU General Public License as published by */
6 /* the Free Software Foundation, either version 3 of the License, or */
7 /* (at your option) any later version. */
8 
9 /* This program is distributed in the hope that it will be useful, */
10 /* but WITHOUT ANY WARRANTY; without even the implied warranty of */
11 /* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
12 /* GNU General Public License for more details. */
13 
14 /* You should have received a copy of the GNU General Public License */
15 /* along with this program. If not, see <http://www.gnu.org/licenses/>. */
16 
17 #include "Common.hpp"
18 #include "diagonalcalc.hpp"
19 #include "Multiply.hpp"
20 #include "wrapperMPI.hpp"
21 #include "mltply.hpp"
22 #include <iostream>
23 
43 int Multiply
44 (
45  struct BindStruct *X
46 )
47 {
48  long int i, i_max;
49  double Ns;
50  int rand_i;
51 
52  i_max = X->Check.idim_max;
53  Ns = 1.0*X->Def.NsiteMPI;
54  // mltply is in expec_energy.cpp v0=H*v1
55 #pragma omp parallel for default(none) private(i,rand_i) \
56  shared(v0, v1,NumAve) firstprivate(i_max, Ns, LargeValue)
57  for (i = 1; i <= i_max; i++) {
58  for (rand_i = 0; rand_i < NumAve; rand_i++) {
59  v0[i][rand_i] = LargeValue * v1[i][rand_i] - v0[i][rand_i] / Ns; //v0=(l-H/Ns)*v1
60  }
61  }
62  NormMPI_dv(i_max, NumAve, v0, global_norm);
63 #pragma omp parallel for default(none) private(i,rand_i) \
64 shared(v0,NumAve,global_norm) firstprivate(i_max)
65  for (i = 1; i <= i_max; i++)
66  for (rand_i = 0; rand_i < NumAve; rand_i++)
67  v0[i][rand_i] = v0[i][rand_i] / global_norm[rand_i];
68  return 0;
69 }
80 (
81  struct BindStruct *X,
82  std::complex<double> **v2
83 )
84 {
85  long int i, i_max;
86  int coef;
87  double dnorm = 0.0;
88  std::complex<double> tmp1 = 1.0;
89  std::complex<double> tmp2 = 0.0;
90  double dt = X->Def.Param.TimeSlice;
91 
92  //Make |v0> = |psi(t+dt)> from |v1> = |psi(t)> and |v0> = H |psi(t)>
93  i_max = X->Check.idim_max;
94  // mltply is in expec_energy.cpp v0=H*v1
95  if (dt < pow(10.0, -14)) {
96 #pragma omp parallel for default(none) private(i) \
97 shared(I,v0, v1, v2) firstprivate(i_max, dt, tmp2)
98  for (i = 1; i <= i_max; i++) {
99  tmp2 = v0[i][0];
100  v0[i][0] = v1[i][0]; //v0=(1-i*dt*H)*v1
101  v1[i][0] = tmp2;
102  v2[i][0] = 0.0 + I * 0.0;
103  }
104  mltply(X, 1, v2, v1);
105  }
106  else {
107  tmp1 *= -I * dt;
108 #pragma omp parallel for default(none) private(i) \
109 shared(v0, v1, v2,I) firstprivate(i_max, dt, tmp1, tmp2)
110  for (i = 1; i <= i_max; i++) {
111  tmp2 = v0[i][0];
112  v0[i][0] = v1[i][0] + tmp1 * tmp2; //v0=(1-i*dt*H)*v1
113  v1[i][0] = tmp2;
114  v2[i][0] = 0.0 + I * 0.0;
115  }
116  for (coef = 2; coef <= X->Def.Param.ExpandCoef; coef++) {
117  tmp1 *= -I * dt / (std::complex<double>)coef;
118  //v2 = H*v1 = H^coef |psi(t)>
119  mltply(X, 1, v2, v1);
120 
121 #pragma omp parallel for default(none) private(i) shared(I, v0, v1, v2) \
122 firstprivate(i_max, tmp1, myrank)
123  for (i = 1; i <= i_max; i++) {
124  v0[i][0] += tmp1 * v2[i][0];
125  v1[i][0] = v2[i][0];
126  v2[i][0] = 0.0 + I * 0.0;
127  }
128  }
129  }
130  dnorm = 0.0;
131 #pragma omp parallel for default(none) reduction(+: dnorm) private(i) shared(v0) \
132 firstprivate(i_max, dt)
133  for (i = 1; i <= i_max; i++) {
134  dnorm += real(conj(v0[i][0])*v0[i][0]);
135  }
136  dnorm = SumMPI_d(dnorm);
137  dnorm = sqrt(dnorm);
138  global_norm[0] = dnorm;
139 #pragma omp parallel for default(none) private(i) shared(v0) firstprivate(i_max, dnorm)
140  for (i = 1; i <= i_max; i++) {
141  v0[i][0] = v0[i][0] / dnorm;
142  }
143  return 0;
144 }
struct DefineList Def
Definision of system (Hamiltonian) etc.
Definition: struct.hpp:395
int NumAve
Definition: global.cpp:43
int Multiply(struct BindStruct *X)
Function of calculating the i-th step norm as and update the i+1-th wave vector as for TPQ calculat...
Definition: Multiply.cpp:44
std::complex< double > ** v0
Definition: global.cpp:20
std::complex< double > I(0.0, 1.0)
int mltply(struct BindStruct *X, int nstate, std::complex< double > **tmp_v0, std::complex< double > **tmp_v1)
Parent function of multiplying the wavefunction by the Hamiltonian. . First, the calculation of diago...
Definition: mltply.cpp:56
void NormMPI_dv(long int ndim, int nstate, std::complex< double > **_v1, double *dnorm)
Compute norm of process-distributed vector .
Definition: wrapperMPI.cpp:344
std::complex< double > ** v1
Definition: global.cpp:21
int MultiplyForTEM(struct BindStruct *X, std::complex< double > **v2)
Function of multiplying Hamiltonian for Time Evolution.
Definition: Multiply.cpp:80
int NsiteMPI
Total number of sites, differ from DefineList::Nsite.
Definition: struct.hpp:57
Bind.
Definition: struct.hpp:394
double TimeSlice
Definition: struct.hpp:33
double * global_norm
Definition: global.cpp:45
struct ParamList Param
Definition: struct.hpp:243
double LargeValue
Definition: global.cpp:42
double SumMPI_d(double norm)
MPI wrapper function to obtain sum of Double across processes.
Definition: wrapperMPI.cpp:222
int ExpandCoef
Definition: struct.hpp:35
struct CheckList Check
Size of the Hilbert space.
Definition: struct.hpp:396
long int idim_max
The dimension of the Hilbert space of this process.
Definition: struct.hpp:305