void do_4index_2_2_tensor_products( bool forwards, const opTypes& optype, const opTypes& rhsType, const opTypes& lhsType, SpinBlock& big, SpinBlock* rhsBlock, SpinBlock* lhsBlock, std::ofstream& ofs, const std::vector<Matrix>& rotateMatrix, const StateInfo *stateinfo ) { Op_component_base& rhs_array = rhsBlock->get_op_array(rhsType); Op_component_base& lhs_array = lhsBlock->get_op_array(lhsType); assert ( (rhs_array.get_size() == 1) || (lhs_array.get_size() == 1) ); // Loop over all rhs operator indices //FIXME copy or reference? std::vector<boost::shared_ptr<SparseMatrix> > rhs_ops; for (int iidx = 0; iidx < rhs_array.get_size(); ++iidx) { rhs_ops = rhs_array.get_local_element(iidx); // Loop over all lhs operator indices std::vector<boost::shared_ptr<SparseMatrix> > lhs_ops; for (int idx = 0; idx < lhs_array.get_size(); ++idx) { lhs_ops = lhs_array.get_local_element(idx); int i = rhs_ops[0]->get_orbs()[0]; int j = rhs_ops[0]->get_orbs()[1]; int k = lhs_ops[0]->get_orbs()[0]; int l = lhs_ops[0]->get_orbs()[1]; // In parallel calculations not all operators are built on each proc if ( ! big.get_op_array(optype).has_local_index(i,j,k,l) ) continue; //pout << "p" << mpigetrank() << "; i,j,k,l = " << i << "," << j << "," << k << "," << l << endl; std::vector<boost::shared_ptr<SparseMatrix> > vec = big.get_op_array(optype).get_element(i,j,k,l); // Loop over rhs spin-op components for (int jjdx=0; jjdx < rhs_ops.size(); jjdx++) { boost::shared_ptr<SparseMatrix>& rhs_op = rhs_ops[jjdx]; assert( rhs_op->get_built() ); const SpinQuantum& spin_12 = rhs_op->get_deltaQuantum(0); // Loop over lhs spin-op components for (int jdx=0; jdx < lhs_ops.size(); jdx++) { boost::shared_ptr<SparseMatrix>& lhs_op = lhs_ops[jdx]; assert( lhs_op->get_built() ); std::string build_12 = rhs_op->get_build_pattern(); std::string build_34 = lhs_op->get_build_pattern(); std::string build_pattern = "(" + build_12 + build_34 + ")"; const SpinQuantum& spin_34 = lhs_op->get_deltaQuantum(0); // Allocate and build new operator for (int sx=0; sx < vec.size(); sx++) { boost::shared_ptr<SparseMatrix>& op = vec[sx]; std::vector<SpinQuantum> s1 = { op->get_quantum_ladder().at(build_pattern).at(0), op->get_quantum_ladder().at(build_pattern).at(1) }; std::vector<SpinQuantum> s2 = { spin_12, spin_34 }; // Select relevant spin components if ( s1 == s2 ) { finish_tensor_product( big, rhsBlock, *rhs_op, *lhs_op, *op, forwards, build_pattern ); // Renormalise operator op->renormalise_transform( rotateMatrix, stateinfo ); } } } } // Store spin-batch on disk if ( ! dmrginp.do_npdm_in_core() ) store_ops_on_disk( ofs, vec ); } } }
void do_4index_3_1_tensor_products( bool forwards, const opTypes& optype, const opTypes& rhsType, const opTypes& lhsType, SpinBlock& big, SpinBlock* rhsBlock, SpinBlock* lhsBlock, std::ofstream& ofs, const std::vector<Matrix>& rotateMatrix, const StateInfo *stateinfo ) { // (i,j,k | l ) partition //------------------------- Op_component_base& rhs_array = rhsBlock->get_op_array(rhsType); Op_component_base& lhs_array = lhsBlock->get_op_array(lhsType); assert ( (rhs_array.get_size() == 1) || (lhs_array.get_size() == 1) ); // Initialize filesystem std::ifstream rhsifs; if ( (! dmrginp.do_npdm_in_core()) && rhsBlock->size() > 1 ) rhsifs.open( rhs_array.get_filename().c_str(), std::ios::binary ); // Loop over all rhs operator indices for (int idx = 0; idx < rhs_array.get_size(); ++idx) { std::vector<boost::shared_ptr<SparseMatrix> > rhs_ops; if ( dmrginp.do_npdm_in_core() || rhsBlock->size() <= 1 ) rhs_ops = rhs_array.get_local_element(idx); else rhs_ops = get_ops_from_disk( rhsifs, rhs_array.get_local_element(0).size() ); // Loop over all lhs operator indices for (int iidx = 0; iidx < lhs_array.get_size(); ++iidx) { std::vector<boost::shared_ptr<SparseMatrix> > lhs_ops = lhs_array.get_local_element(iidx); int i = rhs_ops[0]->get_orbs()[0]; int j = rhs_ops[0]->get_orbs()[1]; int k = rhs_ops[0]->get_orbs()[2]; int l = lhs_ops[0]->get_orbs()[0]; // In parallel calculations not all operators are built on each proc if ( ! big.get_op_array(optype).has_local_index(i,j,k,l) ) continue; //pout << "p" << mpigetrank() << "; i,j,k,l = " << i << "," << j << "," << k << "," << l << endl; std::vector<boost::shared_ptr<SparseMatrix> > vec = big.get_op_array(optype).get_element(i,j,k,l); // Loop over rhs spin-op components for (int jdx=0; jdx < rhs_ops.size(); jdx++) { boost::shared_ptr<SparseMatrix>& rhs_op = rhs_ops[jdx]; assert( rhs_op->get_built() ); std::string build_123 = rhs_op->get_build_pattern(); std::vector<SpinQuantum> spin_123 = rhs_op->get_quantum_ladder().at(build_123); // Loop over lhs spin-op components //FIXME for (int jjdx=0; jjdx < lhs_ops.size(); jjdx++) { boost::shared_ptr<SparseMatrix>& lhs_op = lhs_ops[jjdx]; assert( lhs_op->get_built() ); std::string build_4 = lhs_op->get_build_pattern(); std::string build_pattern = "(" + build_123 + build_4 + ")"; // Allocate and build new operator for (int sx=0; sx < vec.size(); sx++) { boost::shared_ptr<SparseMatrix>& op = vec[sx]; // Select relevant spin components std::vector<SpinQuantum> s = { op->get_quantum_ladder().at(build_pattern).at(0), op->get_quantum_ladder().at(build_pattern).at(1) }; // if ( s == spin_123 ) finish_tensor_product( big, rhsBlock, *rhs_op, Transposeview(lhs_op), *op, forwards, build_pattern ); if ( s == spin_123 ) { finish_tensor_product( big, rhsBlock, *rhs_op, *lhs_op, *op, forwards, build_pattern ); // Renormalise operator op->renormalise_transform( rotateMatrix, stateinfo ); } } } } // Store spin-batch on disk if ( ! dmrginp.do_npdm_in_core() ) store_ops_on_disk( ofs, vec ); } } if ( rhsifs.is_open() ) rhsifs.close(); }
void do_3index_1_2_tensor_products( bool forwards, const opTypes& optype, const opTypes& rhsType, const opTypes& lhsType, SpinBlock& big, SpinBlock* rhsBlock, SpinBlock* lhsBlock, std::ofstream& ofs, const std::vector<Matrix>& rotateMatrix, const StateInfo *stateinfo ) { // (i | j,k ) partition //------------------------- Op_component_base& rhs_array = rhsBlock->get_op_array(rhsType); Op_component_base& lhs_array = lhsBlock->get_op_array(lhsType); assert ( (rhs_array.get_size() == 1) || (lhs_array.get_size() == 1) ); //pout << "tensor_1_2: rhs_size = " << rhs_array.get_size() << "; op = " << rhs_array.get_op_string() << endl; //pout << "tensor_1_2: lhs_size = " << lhs_array.get_size() << "; op = " << lhs_array.get_op_string() << endl; // Initialize filesystem std::ifstream lhsifs; if (( ! dmrginp.do_npdm_in_core()) && lhsBlock->size() > 1) lhsifs.open( lhs_array.get_filename().c_str(), std::ios::binary ); // Loop over all lhs operator indices for (int idx = 0; idx < lhs_array.get_size(); ++idx) { std::vector<boost::shared_ptr<SparseMatrix> > lhs_ops; // Assume 2-index operators are available on this processor in core lhs_ops = lhs_array.get_local_element(idx); // Loop over all rhs operator indices for (int iidx = 0; iidx < rhs_array.get_size(); ++iidx) { std::vector<boost::shared_ptr<SparseMatrix> > rhs_ops = rhs_array.get_local_element(iidx); int i = rhs_ops[0]->get_orbs()[0]; int j = lhs_ops[0]->get_orbs()[0]; int k = lhs_ops[0]->get_orbs()[1]; //pout << "i = " << i << endl; //pout << "j,k = " << j << "," << k << endl; // In parallel calculations not all operators are built on each proc if ( ! big.get_op_array(optype).has_local_index(i,j,k) ) continue; //pout << "building i,j,k = " << i << "," << j << "," << k << endl; std::vector<boost::shared_ptr<SparseMatrix> > vec = big.get_op_array(optype).get_element(i,j,k); //pout << "got i,j,k\n"; // Loop over lhs spin-op components for (int jdx=0; jdx < lhs_ops.size(); jdx++) { boost::shared_ptr<SparseMatrix>& lhs_op = lhs_ops[jdx]; assert( lhs_op->get_built() ); std::string build_23 = lhs_op->get_build_pattern(); //pout << build_23 << endl; //pout << "getting spin_23\n"; std::vector<SpinQuantum> spin_23 = lhs_op->get_quantum_ladder().at(build_23); //pout << "got spin_23\n"; // Loop over rhs spin-op components for (int jjdx=0; jjdx < rhs_ops.size(); jjdx++) { boost::shared_ptr<SparseMatrix>& rhs_op = rhs_ops[jjdx]; assert( rhs_op->get_built() ); std::string build_1 = rhs_op->get_build_pattern(); std::string build_pattern = "(" + build_1 + build_23 + ")"; // Allocate and build new operator for (int sx=0; sx < vec.size(); sx++) { boost::shared_ptr<SparseMatrix>& op = vec[sx]; // Select relevant spin component std::vector<SpinQuantum> s = { op->get_quantum_ladder().at(build_pattern).at(0) }; if ( s == spin_23 ) { finish_tensor_product( big, rhsBlock, *rhs_op, *lhs_op, *op, forwards, build_pattern ); // Renormalise operator op->renormalise_transform( rotateMatrix, stateinfo ); } } } } // Store spin-batch on disk if ( ! dmrginp.do_npdm_in_core() ) store_ops_on_disk( ofs, vec ); } } if ( lhsifs.is_open() ) lhsifs.close(); }