47 for (
int ikappa = 0; ikappa <
nKappa; ikappa++ ){ create_right( ikappa, mps_tensor, mps_tensor, NULL, NULL ); }
49 for (
int ikappa = 0; ikappa <
nKappa; ikappa++ ){ create_left( ikappa, mps_tensor, mps_tensor, NULL, NULL ); }
59 for (
int ikappa = 0; ikappa <
nKappa; ikappa++ ){ create_right( ikappa, mps_tensor_up, mps_tensor_down, previous, workmem ); }
61 for (
int ikappa = 0; ikappa <
nKappa; ikappa++ ){ create_left( ikappa, mps_tensor_up, mps_tensor_down, previous, workmem ); }
66 void CheMPS2::TensorL::create_right(
const int ikappa,
TensorT * mps_tensor_up,
TensorT * mps_tensor_down,
TensorO * previous,
double * workmem ){
69 const int NRdown = NRup + 1;
78 for (
int geval = 0; geval < 2; geval++ ){
96 if ( previous == NULL ){
97 assert( dimLup == dimLdown );
100 double * Tup = mps_tensor_up ->
gStorage( NL, TwoSL, IL, NRup, TwoSRup, IRup );
101 double * Tdown = mps_tensor_down->
gStorage( NL, TwoSL, IL, NRdown, TwoSRdown, IRdown );
107 alpha =
Special::phase( TwoSRdown - TwoSRup + 1 ) * sqrt( ( TwoSRup + 1.0 ) / ( TwoSRdown + 1 ) );
110 dgemm_( &trans, ¬rans, &dimRup, &dimRdown, &dimLup, &alpha, Tup, &dimLup, Tdown, &dimLup, &add,
storage +
kappa2index[ ikappa ], &dimRup );
114 if (( dimLup > 0 ) && ( dimLdown > 0 )){
116 double * Tup = mps_tensor_up ->
gStorage( NL, TwoSL, IL, NRup, TwoSRup, IRup );
117 double * Tdown = mps_tensor_down->
gStorage( NL, TwoSL, IL, NRdown, TwoSRdown, IRdown );
118 double * Opart = previous->
gStorage( NL, TwoSL, IL, NL, TwoSL, IL );
124 alpha =
Special::phase( TwoSRdown - TwoSRup + 1 ) * sqrt( ( TwoSRup + 1.0 ) / ( TwoSRdown + 1 ) );
127 dgemm_( &trans, ¬rans, &dimRup, &dimLdown, &dimLup, &alpha, Tup, &dimLup, Opart, &dimLup, &
set, workmem, &dimRup );
129 dgemm_( ¬rans, ¬rans, &dimRup, &dimRdown, &dimLdown, &one, workmem, &dimRup, Tdown, &dimLdown, &one,
storage +
kappa2index[ ikappa ], &dimRup );
137 void CheMPS2::TensorL::create_left(
const int ikappa,
TensorT * mps_tensor_up,
TensorT * mps_tensor_down,
TensorO * previous,
double * workmem ){
140 const int NLdown = NLup + 1;
149 for (
int geval = 0; geval < 2; geval++ ){
167 if ( previous == NULL ){
168 assert( dimRup == dimRdown );
171 double * Tup = mps_tensor_up ->
gStorage( NLup, TwoSLup, ILup, NR, TwoSR, IR );
172 double * Tdown = mps_tensor_down->
gStorage( NLdown, TwoSLdown, ILdown, NR, TwoSR, IR );
178 alpha =
Special::phase( TwoSLup - TwoSLdown + 1 ) * sqrt( ( TwoSLup + 1.0 ) / ( TwoSLdown + 1 ) );
181 dgemm_( ¬rans, &trans, &dimLup, &dimLdown, &dimRup, &alpha, Tup, &dimLup, Tdown, &dimLdown, &add,
storage +
kappa2index[ ikappa ], &dimLup );
185 if (( dimRup > 0 ) && ( dimRdown > 0 )){
187 double * Tup = mps_tensor_up ->
gStorage( NLup, TwoSLup, ILup, NR, TwoSR, IR );
188 double * Tdown = mps_tensor_down->
gStorage( NLdown, TwoSLdown, ILdown, NR, TwoSR, IR );
189 double * Opart = previous->
gStorage( NR, TwoSR, IR, NR, TwoSR, IR );
195 alpha =
Special::phase( TwoSLup - TwoSLdown + 1 ) * sqrt( ( TwoSLup + 1.0 ) / ( TwoSLdown + 1 ) );
198 dgemm_( ¬rans, ¬rans, &dimLup, &dimRdown, &dimRup, &alpha, Tup, &dimLup, Opart, &dimRup, &
set, workmem, &dimLup );
200 dgemm_( ¬rans, &trans, &dimLup, &dimLdown, &dimRdown, &one, workmem, &dimLup, Tdown, &dimLdown, &one,
storage +
kappa2index[ ikappa ], &dimLup );
int index
Index of the Tensor object. For TensorT: a site index; for other tensors: a boundary index...
void create(TensorT *mps_tensor)
Create a new TensorL.
int * sector_nelec_up
The up particle number sector.
int * sector_spin_down
The down spin symmetry sector (pointer points to sectorTwoS1 if two_j == 0)
int gCurrentDim(const int boundary, const int N, const int TwoS, const int irrep) const
Get the current virtual dimensions.
TensorL(const int boundary_index, const int Idiff, const bool moving_right, const SyBookkeeper *book_up, const SyBookkeeper *book_down)
Constructor.
static int phase(const int power_times_two)
Phase function.
const SyBookkeeper * bk_down
The bookkeeper of the lower MPS.
double * gStorage()
Get the pointer to the storage.
bool moving_right
Whether or not moving right.
int * sector_spin_up
The up spin symmetry sector.
double * gStorage()
Get the pointer to the storage.
int n_irrep
The (real-valued abelian) point group irrep difference between the symmetry sectors of the lower and ...
static int directProd(const int Irrep1, const int Irrep2)
Get the direct product of the irreps with numbers Irrep1 and Irrep2: a bitwise XOR for psi4's convent...
int * sector_irrep_up
The up spin symmetry sector.
virtual ~TensorL()
Destructor.
const SyBookkeeper * bk_up
The bookkeeper of the upper MPS.
int * kappa2index
kappa2index[kappa] indicates the start of tensor block kappa in storage. kappa2index[nKappa] gives th...
void clear()
Set all storage variables to 0.0.
int nKappa
Number of Tensor blocks.
double * storage
The actual variables. Tensor block kappa begins at storage+kappa2index[kappa] and ends at storage+kap...