Reorganization of headers (I): rename JSC -> ABACUS

All files need to be changed to refer to new headers.
First step of the reorganization.
This commit is contained in:
J.-S. Caux
2018-02-10 14:33:07 +01:00
parent 0c893c89f7
commit 63cdd4250c
176 changed files with 8391 additions and 9384 deletions
+28 -42
View File
@@ -2,31 +2,30 @@
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC.h
File: ABACUS.h
Purpose: Core header file, includes all descendents.
***********************************************************/
#ifndef _JSC_H_
#define _JSC_H_
#ifndef ABACUS_H
#define ABACUS_H
// This core header file includes all the others
const char JSC_VERSION[20] = "ABACUS++G_8";
const char ABACUS_VERSION[20] = "ABACUS++G_8";
// Standard includes
#include <cmath>
#include <cmath>
#include <complex> // for complex number algebra
#include <string>
#include <iostream>
#include <fstream>
#include <fstream>
#include <iomanip>
#include <cstdlib> // for exit(), ...
@@ -46,77 +45,64 @@ const char JSC_VERSION[20] = "ABACUS++G_8";
#include <signal.h> /* signal name macros, and the signal() prototype */
// My own math functions and shortcuts
#include "JSC_util.h"
#include "ABACUS_Utils.h"
// Vectors and matrices
#include "JSC_Vect.h" // My vector class definitions
#include "JSC_Matrix.h" // My matrix class definitions
#include "ABACUS_Vect.h" // My vector class definitions
#include "ABACUS_Matrix.h" // My matrix class definitions
// Choose_Table
#include "JSC_Combi.h"
#include "ABACUS_Combi.h"
// Fitting, interpolating
#include "JSC_Fitting.h"
#include "ABACUS_Fitting.h"
// Young tableaux
#include "JSC_Young.h"
#include "ABACUS_Young.h"
// Integration
#include "JSC_Integ.h"
#include "ABACUS_Integ.h"
// Special functions:
#include "JSC_Spec_Fns.h"
#include "ABACUS_Spec_Fns.h"
//*** Integrable models:
// Heisenberg spin-1/2 antiferromagnet
#include "JSC_Heis.h"
#include "ABACUS_Heis.h"
// Lieb-Liniger
#include "JSC_LiebLin.h"
#include "ABACUS_LiebLin.h"
// One-d spinless fermions:
#include "JSC_ODSLF.h"
#include "ABACUS_ODSLF.h"
// General:
//#include "JSC_Bethe.h"
//#include "ABACUS_Bethe.h" // IN DEVELOPMENT
// Thermodynamic Bethe Ansatz utilities
#include "JSC_TBA.h"
#include "ABACUS_TBA.h"
// State ensembles
#include "JSC_State_Ensemble.h"
#include "ABACUS_State_Ensemble.h"
// XXX in zero field: Uq(sl(2)) stuff
#include "JSC_XXX_h0.h"
// XXX in zero field: Vertex Operator Approach
#include "ABACUS_XXX_VOA.h"
// XXZ in zero field: quantum groups
#include "JSC_XXZ_h0.h"
// XXZ in zero field: Vertex Operator Approach
#include "ABACUS_XXZ_VOA.h"
// Two-component Bose gas
//#include "2CBG.h"
// Richardson
//#include "Richardson.h"
// *** Correlation functions:
// New scanning protocols for ABACUS++
#include "JSC_Scan.h"
// Functions for everybody
//#include "JSC_fns.h" // KEEP THIS INCLUDE LAST, SINCE IT USES PREVIOUS DECLARATIONS
#include "ABACUS_Scan.h"
// Numerical RG:
#include "JSC_NRG.h"
// OpenMP
#include <omp.h>
#include "ABACUS_NRG.h"
// Typedefs:
typedef double DP;
#endif // _JSC_H_
#endif // ABACUS_H
+17 -32
View File
@@ -2,36 +2,24 @@
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC_Bethe.h
File: ABACUS_Bethe.h
Purpose: Declares Bethe state-related classes and functions.
Status: IN DEVELOPMENT
***********************************************************/
#ifndef _BETHE_
#define _BETHE_
#ifndef ABACUS_BETHE_H
#define ABACUS_BETHE_H
#include "JSC.h"
#include "ABACUS.h"
namespace JSC {
/*
class Model {
protected:
string Name; // LiebLin, XXZ, XXX, XXZ_gpd
int Nsites; //
int L;
DP interaction;
public:
Model (string Name_ref,
};
*/
namespace ABACUS {
class Base {
@@ -41,7 +29,7 @@ namespace JSC {
Vect<int> Nrap; // Nrap[i] contains the number of rapidities of type i, i = 0, ..., Nstrings - 1.
int Nraptot; // total number of strings in this state
Vect<DP> Ix2_infty; // Ix2_infty[i] contains the max of BAE function for the (half-)integer I[i], i = 0, Nstrings - 1.
Vect<int> Ix2_min;
Vect<int> Ix2_min;
Vect<int> Ix2_max; // Ix2_max[i] contains the integer part of 2*I_infty, with correct parity for base.
string baselabel;
@@ -51,20 +39,19 @@ namespace JSC {
public: // LiebLin constructors
Base (int N); // Constructor for repulsive LiebLin gas case: one type of particle
public: // HEIS constructors
//Base (const Heis_Chain& RefChain, int M); // constructs configuration with all Mdown in one-string of +1 parity // DEPRECATED
Base (const Heis_Chain& RefChain, const Vect<int>& Nrapidities); // sets to Nrapidities vector, and checks consistency
Base (const Heis_Chain& RefChain, string baselabel_ref);
public: // operators
public: // operators
Base& operator= (const Base& RefBase);
bool operator== (const Base& RefBase);
bool operator!= (const Base& RefBase);
public: // member functions
void Compute_Ix2_limits(const Heis_Chain& RefChain); // computes the Ix2_infty and Ix2_max
};
void Compute_Ix2_limits(const Heis_Chain& RefChain); // computes the Ix2_infty and Ix2_max
};
//****************************************************************************
@@ -83,7 +70,7 @@ namespace JSC {
int iK;
DP K;
DP lnnorm;
public: // identification
string label; // this is the relative label by default
Vect<Vect<int> > OriginIx2; // to define the relative label
@@ -94,16 +81,14 @@ namespace JSC {
int iter;
int iter_Newton;
//public: // for descendents, etc
public: // constructors
Bethe_State();
Bethe_State (const Bethe_State& RefState); // copy constructor
Bethe_State (const Bethe_State& OriginState, string label_ref);
Bethe_State (const Bethe_State& OriginState, string label_ref);
LiebLin_Bethe_State& operator= (const LiebLin_Bethe_State& RefState);
} // namespace JSC
} // namespace ABACUS
#endif
+8 -10
View File
@@ -1,25 +1,23 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS++ library.
This software is part of J.-S. Caux's ABACUS library.
Copyright (c) 2006-9.
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC_Combi.h
File: ABACUS_Combi.h
Purpose: Declares combinatorics-related classes and functions.
Last modified: 08/10/2009
***********************************************************/
#ifndef _COMBI_
#define _COMBI_
#ifndef ABACUS_COMBI_H
#define ABACUS_COMBI_H
#include "JSC.h"
#include "ABACUS.h"
namespace JSC {
namespace ABACUS {
//***********************************************************************
@@ -46,6 +44,6 @@ namespace JSC {
std::ostream& operator<< (std::ostream& s, Choose_Table& Ref_table);
} // namespace JSC
} // namespace ABACUS
#endif
@@ -2,26 +2,26 @@
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC.h
File: ABACUS_Fitting.h
Purpose: Core header file, includes all descendents.
Purpose: Defines functions for fitting: linear regression etc.
***********************************************************/
#ifndef _FITTING_
#define _FITTING_
#ifndef ABACUS_FITTING_H
#define ABACUS_FITTING_H
namespace JSC {
namespace ABACUS {
// Functions in src/FITTING directory
void covsrt (SQMat_DP& covar, Vect<bool>& ia, const int mfit);
void lin_reg (Vect_DP x, Vect_DP y, Vect_DP sigma, DP& a, DP& b, DP& chisq);
void lin_reg (Vect_DP x, Vect_DP y, DP& a, DP& b, DP& chisq);
void mrqmin (Vect_DP& x, Vect_DP& y, Vect_DP& sig, Vect_DP& a,
void mrqmin (Vect_DP& x, Vect_DP& y, Vect_DP& sig, Vect_DP& a,
Vect<bool>& ia, SQMat_DP& covar, SQMat_DP& alpha, DP& chisq,
void funcs(const DP, Vect_DP&, DP&, Vect_DP&), DP& alambda);
void mrqcof (Vect_DP& x, Vect_DP& y, Vect_DP& sig, Vect_DP& a,
@@ -30,8 +30,8 @@ namespace JSC {
// For interpolating:
void polint(Vect_DP& xa, Vect_DP& ya, const DP x, DP& y, DP& dy);
void polint(Vect_CX& xa, Vect_CX& ya, const complex<DP> x, complex<DP>& y, complex<DP>& dy);
void polint(Vect_CX& xa, Vect_CX& ya, const std::complex<DP> x, std::complex<DP>& y, std::complex<DP>& dy);
} // namespace JSC
} // namespace ABACUS
#endif
+428
View File
@@ -0,0 +1,428 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: ABACUS_Heis.h
Purpose: Declares Heisenberg chain classes and functions.
***********************************************************/
#ifndef ABACUS_HEIS_H
#define ABACUS_HEIS_H
#include "ABACUS.h"
namespace ABACUS {
// First, some global constants...
const long long int ID_UPPER_LIMIT = 10000000LL; // max size of vectors we can define without seg fault
const int INTERVALS_SIZE = 100000; // size of Scan_Intervals arrays
const int NBASESMAX = 1000; // max number of bases kept
const DP ITER_REQ_PREC = 100.0 * MACHINE_EPS_SQ;
// Cutoffs on particle numbers
const int MAXSTRINGS = 20; // maximal number of particle types we allow in bases
const int NEXC_MAX_HEIS = 16; // maximal number of excitations (string binding/unbinding, particle-hole) considered
//***********************************************************************
class Heis_Chain {
public:
DP J;
DP Delta;
DP anis; // acos(Delta) if Delta < 1.0, 0 if Delta == 1.0, acosh(Delta) if Delta > 1.0
DP hz;
int Nsites;
int Nstrings; // how many possible strings. The following two arrays have Nstrings nonzero elements.
int* Str_L; // vector (length M) containing the allowed string lengths. Elements that are 0 have no meaning.
int* par; // vector (length M) containing the parities of the strings. Elements that are 0 have no meaning.
// Parities are all +1 except for gapless XXZ subcases
DP* si_n_anis_over_2; // for optimization: sin for XXZ, sinh for XXZ_gpd
DP* co_n_anis_over_2; // for optimization
DP* ta_n_anis_over_2; // for optimization
DP prec; // precision required for computations, always put to ITER_REQ_PREC
public:
Heis_Chain ();
Heis_Chain (DP JJ, DP DD, DP hh, int NN); // contructor: simply initializes
Heis_Chain (const Heis_Chain& RefChain); // copy constructor;
Heis_Chain& operator= (const Heis_Chain& RefChain);
bool operator== (const Heis_Chain& RefChain);
bool operator!= (const Heis_Chain& RefChain);
~Heis_Chain(); // destructor
};
//****************************************************************************
// Objects in class Heis_Base are a checked vector containing the number of rapidities of allowable types for a given state
class Heis_Base {
public:
int Mdown; // total number of down spins
Vect<int> Nrap; // Nrap[i] contains the number of rapidities of type i, i = 0, Nstrings - 1.
int Nraptot; // total number of strings in this state
Vect<DP> Ix2_infty; // Ix2_infty[i] contains the max of BAE function for the (half-)integer I[i], i = 0, Nstrings - 1.
Vect<int> Ix2_min;
Vect<int> Ix2_max; // Ix2_max[i] contains the integer part of 2*I_infty, with correct parity for base.
double dimH; // dimension of sub Hilbert space associated to this base; use double to avoid max int problems.
std::string baselabel; // base label
public:
Heis_Base ();
Heis_Base (const Heis_Base& RefBase); // copy constructor
Heis_Base (const Heis_Chain& RefChain, int M); // constructs configuration with all Mdown in one-string of +1 parity
Heis_Base (const Heis_Chain& RefChain, const Vect<int>& Nrapidities); // sets to Nrapidities vector, and checks consistency
Heis_Base (const Heis_Chain& RefChain, std::string baselabel_ref);
inline int& operator[] (const int i);
inline const int& operator[] (const int i) const;
Heis_Base& operator= (const Heis_Base& RefBase);
bool operator== (const Heis_Base& RefBase);
bool operator!= (const Heis_Base& RefBase);
void Compute_Ix2_limits(const Heis_Chain& RefChain); // computes the Ix2_infty and Ix2_max
};
inline int& Heis_Base::operator[] (const int i)
{
return Nrap[i];
}
inline const int& Heis_Base::operator[] (const int i) const
{
return Nrap[i];
}
//****************************************************************************
// Objects in class Lambda carry all rapidities of a state
class Lambda {
private:
int Nstrings;
Vect<int> Nrap;
int Nraptot;
DP** lambda;
public:
Lambda ();
Lambda (const Heis_Chain& RefChain, int M); // constructor, puts all lambda's to zero
Lambda (const Heis_Chain& RefChain, const Heis_Base& base); // constructor, putting I's to lowest-energy config
// consistent with Heis_Base configuration for chain RefChain
Lambda& operator= (const Lambda& RefConfig);
inline DP* operator[] (const int i);
inline const DP* operator[] (const int i) const;
~Lambda();
};
inline DP* Lambda::operator[] (const int i)
{
return lambda[i];
}
inline const DP* Lambda::operator[] (const int i) const
{
return lambda[i];
}
//****************************************************************************
// Objects in class Heis_Bethe_State carry all information about an eigenstate
// Derived classes include XXZ_Bethe_State, XXX_Bethe_State, XXZ_gpd_Bethe_State
// These contain subclass-specific functions and data.
class Heis_Bethe_State {
public:
Heis_Chain chain;
Heis_Base base;
Vect<Vect<int> > Ix2;
Lambda lambda;
Lambda deviation; // string deviations
Lambda BE; // Bethe equation for relevant rapidity, in the form BE = theta - (1/N)\sum ... - \pi I/N = 0
DP diffsq; // sum of squares of rapidity differences in last iteration
int conv; // convergence status
DP dev; // sum of absolute values of string deviations
int iter; // number of iterations necessary for convergence
int iter_Newton; // number of iterations necessary for convergence (Newton method)
DP E; // total energy
int iK; // K = 2.0*PI * iK/Nsites
DP K; // total momentum
DP lnnorm; // ln of norm of reduced Gaudin matrix
std::string label;
public:
Heis_Bethe_State ();
Heis_Bethe_State (const Heis_Bethe_State& RefState); // copy constructor
Heis_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
Heis_Bethe_State (const Heis_Chain& RefChain, const Heis_Base& base); // constructor to lowest-energy config with base
virtual ~Heis_Bethe_State () {};
public:
int Charge () { return(base.Mdown); };
void Set_to_Label (std::string label_ref, const Vect<Vect<int> >& OriginIx2);
void Set_Label_from_Ix2 (const Vect<Vect<int> >& OriginIx2);
bool Check_Symmetry (); // checks whether the I's are symmetrically distributed
void Compute_diffsq (); // \sum BE[j][alpha]^2
void Find_Rapidities (bool reset_rapidities); // Finds the rapidities
void Find_Rapidities_Twisted (bool reset_rapidities, DP twist); // Finds the rapidities with twist added to RHS of logBE
void Solve_BAE_bisect (int j, int alpha, DP req_prec, int itermax);
void Iterate_BAE (DP iter_factor); // Finds new set of lambda[j][alpha] from previous one by simple iteration
void Solve_BAE_straight_iter (DP straight_prec, int max_iter_interp, DP iter_factor);
void Solve_BAE_extrap (DP extrap_prec, int max_iter_extrap, DP iter_factor);
void Iterate_BAE_Newton (); // Finds new set of lambda[j][alpha] from previous one by a Newton step
void Solve_BAE_Newton (DP Newton_prec, int max_iter_Newton);
void Solve_BAE_with_silk_gloves (DP silk_prec, int max_iter_silk, DP iter_factor);
void Compute_lnnorm ();
void Compute_Momentum ();
void Compute_All (bool reset_rapidities); // solves BAE, computes E, K and lnnorm
inline bool Set_to_Inner_Skeleton (int iKneeded, const Vect<Vect<int> >& OriginStateIx2)
{
Ix2[0][0] = Ix2[0][1] - 2;
Ix2[0][base.Nrap[0] - 1] = Ix2[0][base.Nrap[0] - 2] + 2;
(*this).Compute_Momentum();
if (base.Nrap[0] == 0) return(false);
if (iKneeded >= iK) Ix2[0][base.Nrap[0]-1] += 2*(iKneeded - iK);
else Ix2[0][0] += 2*(iKneeded - iK);
if (Ix2[0][0] < base.Ix2_min[0] || Ix2[0][base.Nrap[0]-1] > base.Ix2_max[0]) return(false);
(*this).Set_Label_from_Ix2 (OriginStateIx2);
return(true);
}
void Set_to_Outer_Skeleton (const Vect<Vect<int> >& OriginStateIx2) {
Ix2[0][0] = base.Ix2_min[0] - 4;
Ix2[0][base.Nrap[0]-1] = base.Ix2_max[0] + 4;
(*this).Set_Label_from_Ix2 (OriginStateIx2);
};
void Set_to_Closest_Matching_Ix2_fixed_Base (const Heis_Bethe_State& StateToMatch); // defined in Heis.cc
// Virtual functions, all defined in the derived classes
public:
virtual void Set_Free_lambdas() { ABACUSerror("Heis_Bethe_State::..."); } // sets the rapidities to solutions of BAEs without scattering terms
virtual bool Check_Admissibility(char option) { ABACUSerror("Heis_Bethe_State::..."); return(false); }
// verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
virtual void Compute_BE (int j, int alpha) { ABACUSerror("Heis_Bethe_State::..."); }
virtual void Compute_BE () { ABACUSerror("Heis_Bethe_State::..."); }
virtual DP Iterate_BAE(int i, int alpha) { ABACUSerror("Heis_Bethe_State::..."); return(0.0);}
virtual bool Check_Rapidities() { ABACUSerror("Heis_Bethe_State::..."); return(false); }
virtual DP String_delta () { ABACUSerror("Heis_Bethe_State::..."); return(0.0); }
virtual void Compute_Energy () { ABACUSerror("Heis_Bethe_State::..."); }
virtual void Build_Reduced_Gaudin_Matrix (SQMat<std::complex<DP> >& Gaudin_Red) { ABACUSerror("Heis_Bethe_State::..."); }
};
inline bool Is_Inner_Skeleton (Heis_Bethe_State& State) {
return (State.base.Nrap[0] >= 2 && (State.Ix2[0][0] == State.Ix2[0][1] - 2 || State.Ix2[0][State.base.Nrap[0]-1] == State.Ix2[0][State.base.Nrap[0]-2] + 2));
};
inline bool Is_Outer_Skeleton (Heis_Bethe_State& State) {
return (State.Ix2[0][0] == State.base.Ix2_min[0] - 4 && State.Ix2[0][State.base.Nrap[0]-1] == State.base.Ix2_max[0] + 4);
};
inline bool Force_Descent (char whichDSF, Heis_Bethe_State& ScanState, Heis_Bethe_State& RefState, int desc_type_required, int iKmod, DP Chem_Pot)
{
bool force_descent = false;
// Force descent for all DSFs if we're at K = 0 or PI and not conserving momentum upon descent:
if (desc_type_required > 8 && (2*(ScanState.iK - RefState.iK) % iKmod == 0)) force_descent = true; // type_req > 8 means that we don't conserve momentum
return(force_descent);
}
std::ostream& operator<< (std::ostream& s, const Heis_Bethe_State& state);
//****************************************************************************
// Objects in class XXZ_Bethe_State carry all extra information pertaining to XXZ gapless
class XXZ_Bethe_State : public Heis_Bethe_State {
public:
Lambda sinhlambda;
Lambda coshlambda;
Lambda tanhlambda;
public:
XXZ_Bethe_State ();
XXZ_Bethe_State (const XXZ_Bethe_State& RefState); // copy constructor
XXZ_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
XXZ_Bethe_State (const Heis_Chain& RefChain, const Heis_Base& base); // constructor to lowest-energy config with base
public:
XXZ_Bethe_State& operator= (const XXZ_Bethe_State& RefState);
public:
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
void Compute_sinhlambda();
void Compute_coshlambda();
void Compute_tanhlambda();
bool Check_Admissibility(char option); // verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
void Compute_BE (int j, int alpha);
void Compute_BE ();
DP Iterate_BAE(int i, int j);
bool Check_Rapidities(); // checks that all rapidities are not nan
DP String_delta ();
void Compute_Energy ();
void Build_Reduced_Gaudin_Matrix (SQMat<std::complex<DP> >& Gaudin_Red);
// XXZ specific functions:
public:
};
XXZ_Bethe_State Add_Particle_at_Center (const XXZ_Bethe_State& RefState);
XXZ_Bethe_State Remove_Particle_at_Center (const XXZ_Bethe_State& RefState);
//****************************************************************************
// Objects in class XXX_Bethe_State carry all extra information pertaining to XXX antiferromagnet
class XXX_Bethe_State : public Heis_Bethe_State {
public:
XXX_Bethe_State ();
XXX_Bethe_State (const XXX_Bethe_State& RefState); // copy constructor
XXX_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
XXX_Bethe_State (const Heis_Chain& RefChain, const Heis_Base& base); // constructor to lowest-energy config with base
public:
XXX_Bethe_State& operator= (const XXX_Bethe_State& RefState);
public:
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
bool Check_Admissibility(char option); // verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
void Compute_BE (int j, int alpha);
void Compute_BE ();
DP Iterate_BAE(int i, int j);
bool Check_Rapidities(); // checks that all rapidities are not nan
DP String_delta ();
void Compute_Energy ();
void Build_Reduced_Gaudin_Matrix (SQMat<std::complex<DP> >& Gaudin_Red);
// XXX specific functions
public:
bool Check_Finite_rap ();
};
XXX_Bethe_State Add_Particle_at_Center (const XXX_Bethe_State& RefState);
XXX_Bethe_State Remove_Particle_at_Center (const XXX_Bethe_State& RefState);
//****************************************************************************
// Objects in class XXZ_gpd_Bethe_State carry all extra information pertaining to XXZ gapped antiferromagnets
class XXZ_gpd_Bethe_State : public Heis_Bethe_State {
public:
Lambda sinlambda;
Lambda coslambda;
Lambda tanlambda;
public:
XXZ_gpd_Bethe_State ();
XXZ_gpd_Bethe_State (const XXZ_gpd_Bethe_State& RefState); // copy constructor
XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, const Heis_Base& base); // constructor to lowest-energy config with base
public:
XXZ_gpd_Bethe_State& operator= (const XXZ_gpd_Bethe_State& RefState);
public:
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
void Compute_sinlambda();
void Compute_coslambda();
void Compute_tanlambda();
int Weight(); // weight function for contributions cutoff
bool Check_Admissibility(char option); // verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
void Compute_BE (int j, int alpha);
void Compute_BE ();
DP Iterate_BAE(int i, int j);
void Iterate_BAE_Newton();
bool Check_Rapidities(); // checks that all rapidities are not nan and are in interval ]-PI/2, PI/2]
DP String_delta ();
void Compute_Energy ();
void Build_Reduced_Gaudin_Matrix (SQMat<std::complex<DP> >& Gaudin_Red);
// XXZ_gpd specific functions
public:
};
XXZ_gpd_Bethe_State Add_Particle_at_Center (const XXZ_gpd_Bethe_State& RefState);
XXZ_gpd_Bethe_State Remove_Particle_at_Center (const XXZ_gpd_Bethe_State& RefState);
//***********************************************
// Function declarations
// in M_vs_H.cc
DP Ezero (DP Delta, int N, int M);
DP H_vs_M (DP Delta, int N, int M);
DP HZmin (DP Delta, int N, int M, Vect_DP& Ezero_ref);
int M_vs_H (DP Delta, int N, DP HZ);
DP X_avg (char xyorz, DP Delta, int N, int M);
DP Chemical_Potential (const Heis_Bethe_State& RefState);
DP Particle_Hole_Excitation_Cost (char whichDSF, Heis_Bethe_State& AveragingState);
//DP Sumrule_Factor (char whichDSF, Heis_Bethe_State& RefState, DP Chem_Pot, bool fixed_iK, int iKneeded);
DP Sumrule_Factor (char whichDSF, Heis_Bethe_State& RefState, DP Chem_Pot, int iKmin, int iKmax);
void Evaluate_F_Sumrule (std::string prefix, char whichDSF, const Heis_Bethe_State& RefState, DP Chem_Pot, int iKmin, int iKmax);
std::complex<DP> ln_Sz_ME (XXZ_Bethe_State& A, XXZ_Bethe_State& B);
std::complex<DP> ln_Smin_ME (XXZ_Bethe_State& A, XXZ_Bethe_State& B);
std::complex<DP> ln_Sz_ME (XXX_Bethe_State& A, XXX_Bethe_State& B);
std::complex<DP> ln_Smin_ME (XXX_Bethe_State& A, XXX_Bethe_State& B);
// From Antoine Klauser:
std::complex<DP> ln_Szz_ME (XXX_Bethe_State& A, XXX_Bethe_State& B);
std::complex<DP> ln_Szm_p_Smz_ME (XXX_Bethe_State& A, XXX_Bethe_State& B);
std::complex<DP> ln_Smm_ME (XXX_Bethe_State& A, XXX_Bethe_State& B);
std::complex<DP> ln_Sz_ME (XXZ_gpd_Bethe_State& A, XXZ_gpd_Bethe_State& B);
std::complex<DP> ln_Smin_ME (XXZ_gpd_Bethe_State& A, XXZ_gpd_Bethe_State& B);
DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, XXZ_Bethe_State& LeftState,
XXZ_Bethe_State& RefState, DP Chem_Pot, std::stringstream& DAT_outfile);
DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, XXX_Bethe_State& LeftState,
XXX_Bethe_State& RefState, DP Chem_Pot, std::stringstream& DAT_outfile);
DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, XXZ_gpd_Bethe_State& LeftState,
XXZ_gpd_Bethe_State& RefState, DP Chem_Pot, std::stringstream& DAT_outfile);
// For geometric quench:
std::complex<DP> ln_Overlap (XXX_Bethe_State& A, XXX_Bethe_State& B);
void Scan_Heis_Geometric_Quench (DP Delta, int N_1, int M, long long int base_id_1, long long int type_id_1, long long int id_1,
int N_2, int iKmin, int iKmax, int Max_Secs, bool refine);
} // namespace ABACUS
#endif
+86 -87
View File
@@ -1,31 +1,30 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS++ library.
This software is part of J.-S. Caux's ABACUS library.
Copyright (c)
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC_Integ.h
File: ABACUS_Integ.h
Purpose: Declares combinatorics-related classes and functions.
***********************************************************/
#ifndef _INTEG_
#define _INTEG_
#ifndef ABACUS_INTEG_H
#define ABACUS_INTEG_H
#include "JSC.h"
#include "ABACUS.h"
namespace JSC {
namespace ABACUS {
//********************** Class Domain ************************
template<class T>
class Domain {
private:
Vect<T> bdry;
@@ -35,41 +34,41 @@ namespace JSC {
bdry[0] = T(0);
bdry[1] = T(0);
}
public:
Domain (T xmin_ref, T xmax_ref) : bdry(Vect<T>(2))
{
if (xmax_ref < xmin_ref) JSCerror("Use xmax > xmin in Domain.");
if (xmax_ref < xmin_ref) ABACUSerror("Use xmax > xmin in Domain.");
bdry[0] = xmin_ref;
bdry[1] = xmax_ref;
}
public:
inline T xmin (int i)
{
if (i > bdry.size()/2) JSCerror("i index too high in Domain::xmin.");
return(bdry[2*i]);
}
{
if (i > bdry.size()/2) ABACUSerror("i index too high in Domain::xmin.");
return(bdry[2*i]);
}
public:
inline T xmax (int i)
{
if (i > bdry.size()/2) JSCerror("i index too high in Domain::xmax.");
return(bdry[2*i + 1]);
}
{
if (i > bdry.size()/2) ABACUSerror("i index too high in Domain::xmax.");
return(bdry[2*i + 1]);
}
public:
inline int Ndomains ()
{
return(bdry.size()/2);
}
{
return(bdry.size()/2);
}
public:
void Include (T xmin_ref, T xmax_ref) {
// Determine the indices of xmin_ref & xmax_ref
int xmin_reg = -1;
int xmax_reg = -1;
@@ -79,15 +78,13 @@ namespace JSC {
if ((i+1) % 2 && bdry[i] <= xmax_ref) xmax_reg++;
if (i % 2 && bdry[i] < xmax_ref) xmax_reg++;
}
//cout << "Include: xmin_reg = " << xmin_reg << "\txmax_reg = " << xmax_reg << endl;
Vect<T> new_bdry(bdry.size() + 2 * ((xmin_reg % 2 && xmax_reg % 2) - (xmax_reg - xmin_reg)/2));
int ishift = 0;
for (int i = 0; i <= xmin_reg; ++i) new_bdry[i] = bdry[i];
if (xmin_reg % 2) {
new_bdry[xmin_reg + 1] = xmin_ref;
new_bdry[xmin_reg + 1] = xmin_ref;
ishift++;
if (xmax_reg % 2) {
new_bdry[xmin_reg + 2] = xmax_ref;
@@ -100,15 +97,15 @@ namespace JSC {
}
for (int i = xmin_reg + ishift + 1; i < new_bdry.size(); ++i)
new_bdry[i] = bdry[xmax_reg - xmin_reg - ishift + i];
bdry = new_bdry;
return;
}
public:
void Exclude (T xmin_ref, T xmax_ref) {
// Determine the indices of xmin_ref & xmax_ref
int xmin_reg = -1;
int xmax_reg = -1;
@@ -118,15 +115,13 @@ namespace JSC {
if ((i+1) % 2 && bdry[i] <= xmax_ref) xmax_reg++;
if (i % 2 && bdry[i] < xmax_ref) xmax_reg++;
}
//cout << "Exclude: xmin_reg = " << xmin_reg << "\txmax_reg = " << xmax_reg << endl;
Vect<T> new_bdry(bdry.size() + 2 * (((xmin_reg + 1) % 2 && (xmax_reg + 1) % 2) - (xmax_reg - xmin_reg)/2));
int ishift = 0;
for (int i = 0; i <= xmin_reg; ++i) new_bdry[i] = bdry[i];
if ((xmin_reg + 1) % 2) {
new_bdry[xmin_reg + 1] = xmin_ref;
new_bdry[xmin_reg + 1] = xmin_ref;
ishift++;
if ((xmax_reg + 1) % 2) {
new_bdry[xmin_reg + 2] = xmax_ref;
@@ -139,24 +134,25 @@ namespace JSC {
}
for (int i = xmin_reg + ishift + 1; i < new_bdry.size(); ++i)
new_bdry[i] = bdry[xmax_reg - xmin_reg - ishift + i];
bdry = new_bdry;
return;
}
};
template<class T>
std::ostream& operator<< (std::ostream& s, Domain<T> dom)
{
for (int i = 0; i < dom.Ndomains(); ++i) {
if (i > 0) s << endl;
if (i > 0) s << std::endl;
s << dom.xmin(i) << "\t" << dom.xmax(i);
}
return(s);
}
// ********************************* struct I_table ************************
struct I_table {
@@ -168,11 +164,9 @@ namespace JSC {
DP alpha;
DP logalpha;
DP prec;
//Vect_DP rho_tbl;
//Vect_DP I_tbl;
DP* rho_tbl;
DP* I_tbl;
I_table (DP (*function) (DP, DP), DP rhomin_ref, DP rhomax_ref, int Nvals_ref, DP req_prec);
DP Return_val (DP req_rho);
void Save ();
@@ -195,8 +189,9 @@ namespace JSC {
int maxnrpts;
DP* rho_tbl;
DP* I_tbl;
Integral_table (DP (*function) (DP, DP, int), const char* filenameprefix_ref, DP rhomin_ref, DP rhomax_ref, int Nvals_ref, DP req_prec, int max_nr_pts);
Integral_table (DP (*function) (DP, DP, int), const char* filenameprefix_ref, DP rhomin_ref,
DP rhomax_ref, int Nvals_ref, DP req_prec, int max_nr_pts);
DP Return_val (DP req_rho);
void Save (const char* filenameprefix);
bool Load (const char* filenameprefix, DP rhomin_ref, DP rhomax_ref, int Nvals_ref, DP req_prec, int max_nr_pts);
@@ -207,16 +202,17 @@ namespace JSC {
// ******************************** Recursive integration functions ******************************
DP Integrate_Riemann (DP (*function) (Vect_DP), Vect_DP& args, int arg_to_integ, DP xmin, DP xmax, int Npts);
DP Integrate_Riemann_using_table (DP (*function) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ, I_table Itable,
DP Integrate_Riemann_using_table (DP (*function) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ, I_table Itable,
DP xmin, DP xmax, int Npts);
DP Integrate_rec (DP (*function) (Vect_DP), Vect_DP& args, int arg_to_integ, DP xmin, DP xmax, DP req_prec, int max_rec_level);
DP Integrate_rec_using_table (DP (*function) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ, I_table Itable,
DP Integrate_rec_using_table (DP (*function) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ, I_table Itable,
DP xmin, DP xmax, DP req_prec, int max_rec_level);
DP Integrate_rec_using_table (DP (*function) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ, I_table Itable,
DP xmin, DP xmax, DP req_prec, int max_rec_level, ofstream& outfile);
DP Integrate_rec_using_table_and_file (DP (*function) (Vect_DP, I_table, ofstream&), Vect_DP& args, int arg_to_integ, I_table Itable,
DP xmin, DP xmax, DP req_prec, int max_rec_level, ofstream& outfile);
DP Integrate_rec_using_table (DP (*function) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ, I_table Itable,
DP xmin, DP xmax, DP req_prec, int max_rec_level, std::ofstream& outfile);
DP Integrate_rec_using_table_and_file (DP (*function) (Vect_DP, I_table, std::ofstream&), Vect_DP& args,
int arg_to_integ, I_table Itable,
DP xmin, DP xmax, DP req_prec, int max_rec_level, std::ofstream& outfile);
@@ -240,12 +236,11 @@ namespace JSC {
class Integral_data {
private:
data_pt* data;
data_pt* data;
DP* abs_d2f_dx; // second derivative * dx
DP max_abs_d2f_dx; //
DP max_abs_d2f_dx; //
public:
//int n_vals;
Integral_result integ_res;
public:
@@ -254,37 +249,44 @@ namespace JSC {
public:
Integral_data (DP (*function_ref) (Vect_DP), Vect_DP& args, int arg_to_integ_ref, DP xmin_ref, DP xmax_ref);
Integral_data (DP (*function_ref) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ_ref, I_table Itable, DP xmin_ref, DP xmax_ref);
Integral_data (DP (*function_ref) (Vect_DP, Integral_table), Vect_DP& args, int arg_to_integ_ref, Integral_table Itable, DP xmin_ref, DP xmax_ref);
void Save (ofstream& outfile);
Integral_data (DP (*function_ref) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ_ref,
I_table Itable, DP xmin_ref, DP xmax_ref);
Integral_data (DP (*function_ref) (Vect_DP, Integral_table), Vect_DP& args, int arg_to_integ_ref,
Integral_table Itable, DP xmin_ref, DP xmax_ref);
void Save (std::ofstream& outfile);
void Improve_estimate (DP (*function) (Vect_DP), Vect_DP& args, int arg_to_integ, int Npts_max);
void Improve_estimate (DP (*function) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ, I_table Itable, int Npts_max);
void Improve_estimate (DP (*function) (Vect_DP, Integral_table), Vect_DP& args, int arg_to_integ, Integral_table Itable, int Npts_max);
void Improve_estimate (DP (*function) (Vect_DP, Integral_table), Vect_DP& args, int arg_to_integ,
Integral_table Itable, int Npts_max);
~Integral_data ();
};
Integral_result Integrate_optimal (DP (*function) (Vect_DP), Vect_DP& args, int arg_to_integ, DP xmin, DP xmax, DP req_rel_prec, DP req_abs_prec, int max_nr_pts);
Integral_result Integrate_optimal_using_table (DP (*function) (Vect_DP, I_table Itable), Vect_DP& args, int arg_to_integ,
Integral_result Integrate_optimal (DP (*function) (Vect_DP), Vect_DP& args,
int arg_to_integ, DP xmin, DP xmax, DP req_rel_prec, DP req_abs_prec, int max_nr_pts);
Integral_result Integrate_optimal_using_table (DP (*function) (Vect_DP, I_table Itable), Vect_DP& args, int arg_to_integ,
I_table Itable, DP xmin, DP xmax, DP req_rel_prec, DP req_abs_prec, int max_nr_pts);
Integral_result Integrate_optimal_using_table (DP (*function) (Vect_DP, Integral_table Itable), Vect_DP& args, int arg_to_integ,
Integral_table Itable, DP xmin, DP xmax, DP req_rel_prec, DP req_abs_prec, int max_nr_pts);
Integral_result Integrate_optimal_using_table (DP (*function) (Vect_DP, Integral_table Itable), Vect_DP& args, int arg_to_integ,
Integral_table Itable, DP xmin, DP xmax, DP req_rel_prec,
DP req_abs_prec, int max_nr_pts);
Integral_result Integrate_optimal_using_table (DP (*function) (Vect_DP, I_table Itable), Vect_DP& args, int arg_to_integ,
I_table Itable, DP xmin, DP xmax, DP req_rel_prec,
DP req_abs_prec, int max_nr_pts, std::ofstream& outfile);
Integral_result Integrate_optimal_using_table (DP (*function) (Vect_DP, I_table Itable), Vect_DP& args, int arg_to_integ,
I_table Itable, DP xmin, DP xmax, DP req_rel_prec, DP req_abs_prec, int max_nr_pts, ofstream& outfile);
// ******************************** Recursive version: optimal, complex implementation ******************************
// NB: function returns complex values but takes real arguments
// NB: function returns complex values but takes real arguments
struct data_pt_CX {
DP x;
complex<DP> f;
std::complex<DP> f;
DP dx;
};
struct Integral_result_CX {
complex<DP> integ_est;
std::complex<DP> integ_est;
DP abs_prec;
DP rel_prec;
int n_vals;
@@ -293,12 +295,11 @@ namespace JSC {
class Integral_data_CX {
private:
data_pt_CX* data;
data_pt_CX* data;
DP* abs_d2f_dx; // second derivative * dx
DP max_abs_d2f_dx; //
DP max_abs_d2f_dx; //
public:
//int n_vals;
Integral_result_CX integ_res;
public:
@@ -306,26 +307,24 @@ namespace JSC {
DP xmax;
public:
Integral_data_CX (complex<DP> (*function_ref) (Vect_DP), Vect_DP& args, int arg_to_integ_ref, DP xmin_ref, DP xmax_ref);
//Integral_data_CX (complex<DP> (*function_ref) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ_ref, I_table Itable, DP xmin_ref, DP xmax_ref);
void Save (ofstream& outfile);
void Improve_estimate (complex<DP> (*function) (Vect_DP), Vect_DP& args, int arg_to_integ, int Npts_max);
//void Improve_estimate (complex<DP> (*function) (Vect_DP, I_table), Vect_DP& args, int arg_to_integ, I_table Itable, int Npts_max);
Integral_data_CX (std::complex<DP> (*function_ref) (Vect_DP), Vect_DP& args, int arg_to_integ_ref, DP xmin_ref, DP xmax_ref);
void Save (std::ofstream& outfile);
void Improve_estimate (std::complex<DP> (*function) (Vect_DP), Vect_DP& args, int arg_to_integ, int Npts_max);
~Integral_data_CX ();
};
Integral_result_CX Integrate_optimal (complex<DP> (*function) (Vect_DP), Vect_DP& args, int arg_to_integ, DP xmin, DP xmax,
Integral_result_CX Integrate_optimal (std::complex<DP> (*function) (Vect_DP), Vect_DP& args, int arg_to_integ, DP xmin, DP xmax,
DP req_rel_prec, DP req_abs_prec, int max_nr_pts);
//Integral_result_CX Integrate_optimal_using_table (DP (*function) (Vect_DP, I_table Itable), Vect_DP& args, int arg_to_integ,
//Integral_result_CX Integrate_optimal_using_table (DP (*function) (Vect_DP, I_table Itable), Vect_DP& args, int arg_to_integ,
// I_table Itable, DP xmin, DP xmax, DP req_rel_prec, DP req_abs_prec, int max_nr_pts);
//Integral_result Integrate_optimal_using_table (DP (*function) (Vect_DP, I_table Itable), Vect_DP& args, int arg_to_integ,
// I_table Itable, DP xmin, DP xmax, DP req_rel_prec, DP req_abs_prec, int max_nr_pts, ofstream& outfile);
//Integral_result_CX Integrate_optimal_using_table (DP (*function) (Vect_DP, I_table Itable), Vect_DP& args, int arg_to_integ,
// I_table Itable, DP xmin, DP xmax, DP req_rel_prec, DP req_abs_prec, int max_nr_pts, std::ofstream& outfile);
} // namespace JSC
} // namespace ABACUS
#endif
@@ -2,49 +2,46 @@
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC_LiebLin.h
File: ABACUS_LiebLin.h
Purpose: Declares LiebLin gas-related classes and functions.
***********************************************************/
#ifndef _LIEBLIN_
#define _LIEBLIN_
#ifndef ABACUS_LIEBLIN_H
#define ABACUS_LIEBLIN_H
#include "JSC.h"
#include "ABACUS.h"
namespace JSC {
namespace ABACUS {
// First, some global constants...
//const DP ITER_REQ_PREC_LIEBLIN = 1.0e+6 * MACHINE_EPS_SQ;
const DP ITER_REQ_PREC_LIEBLIN = 1.0e+4 * MACHINE_EPS_SQ;
const int LIEBLIN_Ix2_MIN = -1000000; // Like a UV cutoff. Assumption: never reached in scanning.
const int LIEBLIN_Ix2_MAX = -LIEBLIN_Ix2_MIN;
//***********************************************************************
//class LiebLin_Bethe_State : public Bethe_State {
class LiebLin_Bethe_State {
public:
DP c_int; // interaction parameter
DP L;
DP L;
DP cxL;
int N;
string label;
//Vect<int> OriginStateIx2; // quantum numbers of state on which excitations are built; always ordered
std::string label;
Vect<int> Ix2_available; // quantum numbers which are allowable but not occupied
Vect<int> index_first_hole_to_right;
Vect<int> displacement;
Vect<int> Ix2;
Vect<DP> lambdaoc;
//Vect<DP> BE;
Vect<DP> S; // scattering sum
Vect<DP> dSdlambdaoc; // its derivative
DP diffsq;
@@ -62,9 +59,9 @@ namespace JSC {
LiebLin_Bethe_State& operator= (const LiebLin_Bethe_State& RefState);
public:
int Charge () { return(N); };
void Set_to_Label (string label_ref, const Vect<int>& OriginStateIx2);
void Set_to_Label (string label_ref); // assumes OriginState == GroundState
int Charge () { return(N); };
void Set_to_Label (std::string label_ref, const Vect<int>& OriginStateIx2);
void Set_to_Label (std::string label_ref); // assumes OriginState == GroundState
void Set_Label_from_Ix2 (const Vect<int>& OriginStateIx2);
void Set_Label_Internals_from_Ix2 (const Vect<int>& OriginStateIx2);
bool Check_Admissibility(char whichDSF); // always returns true
@@ -88,7 +85,7 @@ namespace JSC {
void Parity_Flip (); // takes all lambdaoc to -lambdaoc
inline bool Set_to_Inner_Skeleton (int iKneeded, const Vect<int>& OriginIx2)
{
if (N < 3) JSCerror("N<3 incompatible with fixed momentum scanning");
if (N < 3) ABACUSerror("N<3 incompatible with fixed momentum scanning");
Ix2[0] = Ix2[1] - 2;
Ix2[N-1] = Ix2[N-2] + 2;
(*this).Compute_Momentum();
@@ -98,27 +95,28 @@ namespace JSC {
(*this).Set_Label_from_Ix2 (OriginIx2);
return(true);
}
void Set_to_Outer_Skeleton (const Vect<int>& OriginIx2)
{
Ix2[0] = LIEBLIN_Ix2_MIN + (N % 2) + 1;
Ix2[N-1] = LIEBLIN_Ix2_MAX - (N % 2) - 1;
void Set_to_Outer_Skeleton (const Vect<int>& OriginIx2)
{
Ix2[0] = LIEBLIN_Ix2_MIN + (N % 2) + 1;
Ix2[N-1] = LIEBLIN_Ix2_MAX - (N % 2) - 1;
(*this).Set_Label_from_Ix2 (OriginIx2);
//cout << "Set state to outer skeleton: Ix2 " << (*this).Ix2 << endl;
//cout << "label " << (*this).label << endl;
};
};
inline bool Is_Inner_Skeleton (LiebLin_Bethe_State& State) {
return (State.N >= 2 && (State.Ix2[0] == State.Ix2[1] - 2 || State.Ix2[State.N-1] == State.Ix2[State.N-2] + 2));
};
inline bool Is_Outer_Skeleton (LiebLin_Bethe_State& State) {
return (State.N >= 2 && State.Ix2[0] == LIEBLIN_Ix2_MIN + (State.N % 2) + 1 && State.Ix2[State.N-1] == LIEBLIN_Ix2_MAX - (State.N % 2) - 1);
};
inline bool Is_Outer_Skeleton (const LiebLin_Bethe_State& State) {
return (State.N >= 2 && State.Ix2[0] == LIEBLIN_Ix2_MIN + (State.N % 2) + 1 && State.Ix2[State.N-1] == LIEBLIN_Ix2_MAX - (State.N % 2) - 1);
};
inline bool Is_Inner_Skeleton (LiebLin_Bethe_State& State) {
return (State.N >= 2 && (State.Ix2[0] == State.Ix2[1] - 2 || State.Ix2[State.N-1] == State.Ix2[State.N-2] + 2));
};
inline bool Is_Outer_Skeleton (LiebLin_Bethe_State& State) {
return (State.N >= 2 && State.Ix2[0] == LIEBLIN_Ix2_MIN + (State.N % 2) + 1
&& State.Ix2[State.N-1] == LIEBLIN_Ix2_MAX - (State.N % 2) - 1);
};
inline bool Is_Outer_Skeleton (const LiebLin_Bethe_State& State) {
return (State.N >= 2 && State.Ix2[0] == LIEBLIN_Ix2_MIN + (State.N % 2) + 1
&& State.Ix2[State.N-1] == LIEBLIN_Ix2_MAX - (State.N % 2) - 1);
};
inline bool Force_Descent (char whichDSF, LiebLin_Bethe_State& ScanState, LiebLin_Bethe_State& RefState, int desc_type_required, int iKmod, DP Chem_Pot)
inline bool Force_Descent (char whichDSF, LiebLin_Bethe_State& ScanState, LiebLin_Bethe_State& RefState,
int desc_type_required, int iKmod, DP Chem_Pot)
{
bool forcedesc = false;
@@ -138,9 +136,12 @@ namespace JSC {
DP Chemical_Potential (LiebLin_Bethe_State& RefState);
DP Sumrule_Factor (char whichDSF, LiebLin_Bethe_State& RefState, DP Chem_Pot, int iKmin, int iKmax);
void Evaluate_F_Sumrule (char whichDSF, const LiebLin_Bethe_State& RefState, DP Chem_Pot, int iKmin, int iKmax, const char* RAW_Cstr, const char* FSR_Cstr);
void Evaluate_F_Sumrule (string prefix, char whichDSF, const LiebLin_Bethe_State& RefState, DP Chem_Pot, int iKmin, int iKmax);
void Evaluate_F_Sumrule (char whichDSF, DP c_int, DP L, int N, DP kBT, int nstates_req, DP Chem_Pot, int iKmin, int iKmax, const char* FSR_Cstr);
void Evaluate_F_Sumrule (char whichDSF, const LiebLin_Bethe_State& RefState, DP Chem_Pot,
int iKmin, int iKmax, const char* RAW_Cstr, const char* FSR_Cstr);
void Evaluate_F_Sumrule (std::string prefix, char whichDSF, const LiebLin_Bethe_State& RefState,
DP Chem_Pot, int iKmin, int iKmax);
void Evaluate_F_Sumrule (char whichDSF, DP c_int, DP L, int N, DP kBT, int nstates_req,
DP Chem_Pot, int iKmin, int iKmax, const char* FSR_Cstr);
// in LiebLin_Utils.cc
DP LiebLin_dE0_dc (DP c_int, DP L, int N);
@@ -152,32 +153,22 @@ namespace JSC {
DP Particle_Hole_Excitation_Cost (char whichDSF, LiebLin_Bethe_State& AveragingState);
complex<DP> ln_Density_ME (LiebLin_Bethe_State& lstate, LiebLin_Bethe_State& rstate);
complex<DP> ln_Psi_ME (LiebLin_Bethe_State& lstate, LiebLin_Bethe_State& rstate);
complex<DP> ln_g2_ME (LiebLin_Bethe_State& mu, LiebLin_Bethe_State& lambda);
std::complex<DP> ln_Density_ME (LiebLin_Bethe_State& lstate, LiebLin_Bethe_State& rstate);
std::complex<DP> ln_Psi_ME (LiebLin_Bethe_State& lstate, LiebLin_Bethe_State& rstate);
std::complex<DP> ln_g2_ME (LiebLin_Bethe_State& mu, LiebLin_Bethe_State& lambda);
//DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, LiebLin_Bethe_State& LeftState,
// LiebLin_Bethe_State& RefState, DP Chem_Pot, fstream& DAT_outfile);
DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, LiebLin_Bethe_State& LeftState,
LiebLin_Bethe_State& RefState, DP Chem_Pot, stringstream& DAT_outfile);
DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, LiebLin_Bethe_State& LeftState,
LiebLin_Bethe_State& RefState, DP Chem_Pot, std::stringstream& DAT_outfile);
DP LiebLin_Twisted_lnnorm (Vect<complex<DP> >& lambdaoc, double cxL);
complex<DP> LiebLin_Twisted_ln_Overlap (DP expbeta, Vect<DP> lstate_lambdaoc, DP lstate_lnnorm, LiebLin_Bethe_State& rstate);
complex<DP> LiebLin_Twisted_ln_Overlap (complex<DP> expbeta, Vect<complex<DP> > lstate_lambdaoc, DP lstate_lnnorm, LiebLin_Bethe_State& rstate);
complex<DP> LiebLin_ln_Overlap (Vect<DP> lstate_lambdaoc, DP lstate_lnnorm, LiebLin_Bethe_State& rstate);
complex<DP> LiebLin_ln_Overlap (Vect<complex<DP> > lstate_lambdaoc, DP lstate_lnnorm, LiebLin_Bethe_State& rstate);
DP LiebLin_Twisted_lnnorm (Vect<std::complex<DP> >& lambdaoc, double cxL);
std::complex<DP> LiebLin_Twisted_ln_Overlap (DP expbeta, Vect<DP> lstate_lambdaoc, DP lstate_lnnorm, LiebLin_Bethe_State& rstate);
std::complex<DP> LiebLin_Twisted_ln_Overlap (std::complex<DP> expbeta, Vect<std::complex<DP> > lstate_lambdaoc, DP lstate_lnnorm, LiebLin_Bethe_State& rstate);
std::complex<DP> LiebLin_ln_Overlap (Vect<DP> lstate_lambdaoc, DP lstate_lnnorm, LiebLin_Bethe_State& rstate);
std::complex<DP> LiebLin_ln_Overlap (Vect<std::complex<DP> > lstate_lambdaoc, DP lstate_lnnorm, LiebLin_Bethe_State& rstate);
// In src/LiebLin_Tgt0.cc:
//DP Entropy_rho (LiebLin_Bethe_State& RefState, int Delta);
//DP Entropy_Fixed_Delta (LiebLin_Bethe_State& RefState, int Delta);
//DP Entropy (LiebLin_Bethe_State& RefState, int Delta);
DP Entropy (LiebLin_Bethe_State& RefState);
//DP Canonical_Free_Energy (LiebLin_Bethe_State& RefState, DP kBT, int Delta);
DP Canonical_Free_Energy (LiebLin_Bethe_State& RefState, DP kBT);
//DP Entropy (LiebLin_Bethe_State& RefState, DP epsilon);
//DP Canonical_Free_Energy (LiebLin_Bethe_State& RefState, DP kBT, DP epsilon);
//LiebLin_Bethe_State Canonical_Saddle_Point_State (DP c_int, DP L, int N, DP kBT, int Delta);
//LiebLin_Bethe_State Canonical_Saddle_Point_State (DP c_int, DP L, int N, DP kBT, DP epsilon);
LiebLin_Bethe_State Canonical_Saddle_Point_State (DP c_int, DP L, int N, DP kBT);
LiebLin_Bethe_State Add_Particle_at_Center (const LiebLin_Bethe_State& RefState);
LiebLin_Bethe_State Remove_Particle_at_Center (const LiebLin_Bethe_State& RefState);
@@ -185,6 +176,6 @@ namespace JSC {
DP rho_of_lambdaoc_2 (LiebLin_Bethe_State& RefState, DP lambdaoc, DP delta);
} // namespace JSC
} // namespace ABACUS
#endif
+440
View File
@@ -0,0 +1,440 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: ABACUS_Matrix.h
Purpose: Declares square matrix class.
***********************************************************/
#ifndef ABACUS_MATRIX_H
#define ABACUS_MATRIX_H
namespace ABACUS {
// CLASS DEFINITIONS
template <class T>
class SQMat {
private:
int dim;
T** M;
public:
SQMat (int N); // initializes all elements of this n by n matrix to zero
SQMat (const SQMat& rhs); // copy constructor
SQMat (const T& a, int N); // initialize to diagonal matrix with value a (NOT like in NR !!!)
SQMat (const SQMat& a, const SQMat& b); // initialize to tensor product of a and b
SQMat (const SQMat& a, int row_id, int col_id); // init by cutting row row_id and col col_id
void Print ();
SQMat& operator= (const SQMat& rhs); // assignment
SQMat& operator= (const T& a); // assign 1 to diagonal elements (NOT like in NR !!!)
inline T* operator[] (const int i); // subscripting: pointer to row i
inline const T* operator[] (const int i) const;
SQMat& operator+= (const T& a);
SQMat& operator+= (const SQMat& a);
SQMat& operator-= (const T& a);
SQMat& operator-= (const SQMat& a);
SQMat& operator*= (const T& a);
SQMat& operator*= (const SQMat& a);
inline int size() const;
~SQMat();
};
template <class T>
SQMat<T>::SQMat (int N) : dim(N) , M(new T*[N])
{
M[0] = new T[N*N];
for (int i = 1; i < N; i++) M[i] = M[i-1] + N;
}
template <class T>
SQMat<T>::SQMat (const SQMat& rhs) : dim(rhs.dim) , M(new T*[dim])
{
int i,j;
M[0] = new T[dim*dim];
for (i = 1; i < dim; i++) M[i] = M[i-1] + dim;
for (i = 0; i < dim; i++)
for (j = 0; j < dim; j++) M[i][j] = rhs[i][j];
}
template <class T>
SQMat<T>::SQMat (const T& a, int N) : dim(N) , M(new T*[dim])
{
int i, j;
M[0] = new T[dim*dim];
for (i = 1; i < dim; i++) M[i] = M[i-1] + dim;
for (i = 0; i < dim; i++) {
for (j = 0; j < dim; j++) M[i][j] = T(0);
M[i][i] = a;
}
}
template <class T>
SQMat<T>::SQMat (const SQMat& a, const SQMat& b) : dim (a.dim * b.dim) , M(new T*[a.dim * b.dim])
{
M[0] = new T[a.dim * b.dim * a.dim * b.dim];
for (int i = 1; i < a.dim * b.dim; ++i) M[i] = M[i-1] + a.dim * b.dim;
for (int i1 = 0; i1 < a.dim; ++i1) {
for (int i2 = 0; i2 < a.dim; ++i2) {
for (int j1 = 0; j1 < b.dim; ++j1) {
for (int j2 = 0; j2 < b.dim; ++j2) {
M[i1 * (b.dim) + j1][i2 * (b.dim) + j2] = a[i1][i2] * b[j1][j2];
}
}
}
}
}
template <class T>
SQMat<T>::SQMat (const SQMat&a, int row_id, int col_id) : dim (a.dim - 1) , M(new T*[dim])
{
if (dim == 0) {
ABACUSerror("Error: chopping a row and col from size one matrix.");
exit(1);
}
M[0] = new T[dim * dim];
for (int i = 1; i < dim; ++i) M[i] = M[i-1] + dim;
for (int i = 0; i < row_id; ++i)
for (int j = 0; j < col_id; ++j) M[i][j] = a[i][j];
for (int i = row_id; i < dim; ++i)
for (int j = 0; j < col_id; ++j) M[i][j] = a[i+1][j];
for (int i = 0; i < row_id; ++i)
for (int j = col_id; j < dim; ++j) M[i][j] = a[i][j+1];
for (int i = row_id; i < dim; ++i)
for (int j = col_id; j < dim; ++j) M[i][j] = a[i+1][j+1];
}
// operators
template <class T>
void SQMat<T>::Print ()
{
std::cout << std::endl;
for (int i = 0; i < dim; ++i) {
for (int j = 0; j < dim; ++j) std::cout << M[i][j] << " ";
std::cout << std::endl;
}
std::cout << std::endl;
}
template <class T>
SQMat<T>& SQMat<T>::operator= (const SQMat<T>& rhs)
{
if (this != &rhs) {
if (dim != rhs.dim) {
ABACUSerror("Assignment between matrices of different dimensions. Bailing out.");
exit(1);
}
for (int i = 0; i < dim; ++i)
for (int j = 0; j < dim; ++j) M[i][j] = rhs[i][j];
}
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator= (const T& a)
{
for (int i = 0; i < dim; ++i) {
for (int j = 0; j < dim; ++j)
M[i][j] = T(0);
M[i][i] = a;
}
return *this;
}
template <class T>
inline T* SQMat<T>::operator[] (const int i)
{
return M[i];
}
template <class T>
inline const T* SQMat<T>::operator[] (const int i) const
{
return M[i];
}
template <class T>
SQMat<T>& SQMat<T>::operator+= (const T& a)
{
for (int i = 0; i < dim; ++i) M[i][i] += a;
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator+= (const SQMat<T>& a)
{
if (dim != a.dim) {
ABACUSerror("Incompatible matrix sizes in matrix operator +.");
exit(1);
}
for (int i = 0; i < dim; ++i) {
for (int j = 0; j < dim; ++j) {
M[i][j] += a[i][j];
}
}
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator-= (const T& a)
{
for (int i = 0; i < dim; ++i) M[i][i] -= a;
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator-= (const SQMat<T>& a)
{
if (dim != a.dim) {
ABACUSerror("Incompatible matrix sizes in matrix operator +.");
exit(1);
}
for (int i = 0; i < dim; ++i) {
for (int j = 0; j < dim; ++j) {
M[i][j] -= a[i][j];
}
}
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator*= (const T& a)
{
for (int i = 0; i < dim; ++i) for (int j = 0; j < dim; ++j) M[i][j] *= a;
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator*= (const SQMat<T>& a)
{
if (dim != a.dim) {
ABACUSerror("Incompatible matrix sizes in matrix operator *.");
exit(1);
}
SQMat<T> leftarg(*this); // use copy constructor.
for (int i = 0; i < dim; ++i) {
for (int j = 0; j < dim; ++j) {
M[i][j] = 0.0;
for (int k = 0; k < dim; ++k) {
M[i][j] += leftarg[i][k] * a[k][j];
}
}
}
return *this;
}
template <class T>
inline int SQMat<T>::size() const
{
return dim;
}
template <class T>
SQMat<T>::~SQMat()
{
if (M != 0) {
delete[] (M[0]);
delete[] (M);
}
}
//*****************************
template <class T>
class RecMat {
private:
int nrows;
int ncols;
T** M;
public:
RecMat (int Nrows, int Ncols); // initializes all elements of this n by n matrix to zero
RecMat (const T& a, int Nrows, int Ncols);
RecMat (const RecMat& rhs); // copy constructor
void Print ();
RecMat& operator= (const RecMat& rhs); // assignment
inline T* operator[] (const int i); // subscripting: pointer to row i
inline const T* operator[] (const int i) const;
inline int nr_rows() const;
inline int nr_cols() const;
~RecMat();
};
template <class T>
RecMat<T>::RecMat (int Nrows, int Ncols) : nrows(Nrows), ncols(Ncols), M(new T*[Nrows])
{
M[0] = new T[Nrows*Ncols];
for (int i = 1; i < Nrows; i++) M[i] = M[i-1] + Ncols;
for (int i = 0; i < Nrows; i++) for (int j = 0; j < Ncols; j++) M[i][j] = T(0);
}
template <class T>
RecMat<T>::RecMat (const T& a, int Nrows, int Ncols) : nrows(Nrows), ncols(Ncols), M(new T*[Nrows])
{
M[0] = new T[Nrows*Ncols];
for (int i = 1; i < Nrows; i++) M[i] = M[i-1] + Ncols;
for (int i = 0; i < Nrows; i++) for (int j = 0; j < Ncols; j++) {
if (i == j) M[i][i] = a;
else M[i][j] = T(0);
}
}
template <class T>
RecMat<T>::RecMat (const RecMat& rhs) : nrows(rhs.nrows), ncols(rhs.ncols), M(new T*[nrows])
{
int i,j;
M[0] = new T[nrows*ncols];
for (i = 1; i < nrows; i++) M[i] = M[i-1] + ncols;
for (i = 0; i < nrows; i++)
for (j = 0; j < ncols; j++) M[i][j] = rhs[i][j];
}
// operators
template <class T>
void RecMat<T>::Print ()
{
std::cout << std::endl;
for (int i = 0; i < nrows; ++i) {
for (int j = 0; j < ncols; ++j) std::cout << M[i][j] << " ";
std::cout << std::endl;
}
std::cout << std::endl;
}
template <class T>
RecMat<T>& RecMat<T>::operator= (const RecMat<T>& rhs)
{
if (this != &rhs) {
if (nrows != rhs.nrows || ncols != rhs.ncols) {
if (M != 0) {
delete[] (M[0]);
delete[] (M);
}
nrows = rhs.nrows;
ncols = rhs.ncols;
M = new T*[nrows];
M[0] = new T[nrows * ncols];
}
for (int i = 0; i < nrows; ++i)
for (int j = 0; j < ncols; ++j) M[i][j] = rhs[i][j];
}
return *this;
}
template <class T>
inline T* RecMat<T>::operator[] (const int i)
{
return M[i];
}
template <class T>
inline const T* RecMat<T>::operator[] (const int i) const
{
return M[i];
}
template <class T>
inline int RecMat<T>::nr_rows() const
{
return nrows;
}
template <class T>
inline int RecMat<T>::nr_cols() const
{
return ncols;
}
template <class T>
inline std::ostream& operator<< (std::ostream& s, const RecMat<T>& matrix)
{
for (int i = 0; i < matrix.nr_rows(); ++i) {
for (int j = 0; j < matrix.nr_cols(); ++j) s << matrix[i][j] << " ";
s << std::endl;
}
return (s);
}
template <class T>
RecMat<T>::~RecMat()
{
if (M != 0) {
delete[] (M[0]);
delete[] (M);
}
}
// TYPEDEFS:
typedef ABACUS::SQMat<DP> SQMat_DP;
typedef ABACUS::SQMat<std::complex<double> > SQMat_CX;
// FUNCTION DEFINITIONS
// Functions in src/MATRIX directory
DP det_LU (SQMat_DP a);
DP lndet_LU (SQMat_DP a);
std::complex<DP> lndet_LU_dstry (SQMat_DP& a);
std::complex<DP> det_LU_CX (SQMat_CX a);
std::complex<DP> lndet_LU_CX (SQMat_CX a);
std::complex<DP> lndet_LU_CX_dstry (SQMat_CX& a);
void eigsrt (Vect_DP& d, SQMat_DP& v);
void balanc (SQMat_DP& a);
void elmhes (SQMat_DP& a);
void gaussj (SQMat_DP& a, SQMat_DP& b);
void hqr (SQMat_DP& a, Vect_CX& wri);
void jacobi (SQMat_DP& a, Vect_DP& d, SQMat_DP& v, int& nrot);
void lubksb (SQMat_DP& a, Vect_INT& indx, Vect_DP& b);
void lubksb_CX (SQMat_CX& a, Vect_INT& indx, Vect_CX& b);
void ludcmp (SQMat_DP& a, Vect_INT& indx, DP& d);
void ludcmp_CX (SQMat_CX& a, Vect_INT& indx, DP& d);
DP pythag(DP a, DP b);
void tqli(Vect_DP& d, Vect_DP& e, SQMat_DP& z);
void tred2 (SQMat_DP& a, Vect_DP& d, Vect_DP& e);
} // namespace ABACUS
#endif
+35
View File
@@ -0,0 +1,35 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: ABACUS_NRG.h
Purpose: Declares NRG-related classes and functions.
***********************************************************/
#ifndef ABACUS_NRG_H
#define ABACUS_NRG_H
#include "ABACUS.h"
namespace ABACUS {
DP K_Weight_integrand (Vect_DP args); // weighing function for state selection
void Select_States_for_NRG (DP c_int, DP L, int N, int iKmin, int iKmax, int Nstates_required,
bool symmetric_states, int iKmod,
int weighing_option, Vect<std::complex <DP> >& FT_of_potential);
void Build_DFF_Matrix_Block_for_NRG (DP c_int, DP L, int N, int iKmin, int iKmax, int Nstates_required,
bool symmetric_states, int iKmod, int weighing_option,
int label_left_begin, int label_left_end, int label_right_begin, int label_right_end,
int block_option, DP* DFF_block_1, DP* DFF_block_2, Vect_DP Kweight);
}
#endif
+110 -145
View File
@@ -2,22 +2,22 @@
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: Heis.h
File: ABACUS_ODSLF.h
Purpose: Declares lattice spinless fermion classes and functions.
***********************************************************/
#ifndef _ODSLF_
#define _ODSLF_
#ifndef ABACUS_ODSLF_H
#define ABACUS_ODSLF_H
#include "JSC.h"
#include "ABACUS.h"
namespace JSC {
namespace ABACUS {
//****************************************************************************
@@ -40,12 +40,12 @@ namespace JSC {
ODSLF_Base (const Heis_Chain& RefChain, const Vect<int>& Nrapidities); // sets to Nrapidities vector, and checks consistency
ODSLF_Base (const Heis_Chain& RefChain, long long int id_ref);
inline int& operator[] (const int i);
inline const int& operator[] (const int i) const;
inline const int& operator[] (const int i) const;
ODSLF_Base& operator= (const ODSLF_Base& RefBase);
bool operator== (const ODSLF_Base& RefBase);
bool operator!= (const ODSLF_Base& RefBase);
void Compute_Ix2_limits(const Heis_Chain& RefChain); // computes the Ix2_infty and Ix2_max
void Compute_Ix2_limits(const Heis_Chain& RefChain); // computes the Ix2_infty and Ix2_max
void Scan_for_Possible_Types (Vect<long long int>& possible_type_id, int& nfound, int base_level, Vect<int>& Nexcitations);
Vect<long long int> Possible_Types (); // returns a vector of possible types
@@ -56,19 +56,19 @@ namespace JSC {
{
return Nrap[i];
}
inline const int& ODSLF_Base::operator[] (const int i) const
{
return Nrap[i];
}
//****************************************************************************
// Objects in class ODSLF_Ix2_Config carry all the I's of a given state
class ODSLF_Ix2_Config {
//private:
public:
int Nstrings;
Vect<int> Nrap;
@@ -76,73 +76,63 @@ namespace JSC {
int** Ix2;
//Vect<Vect<int> > Ix2;
public:
ODSLF_Ix2_Config ();
ODSLF_Ix2_Config (const Heis_Chain& RefChain, int M); // constructor, puts I's to ground state
ODSLF_Ix2_Config (const Heis_Chain& RefChain, const ODSLF_Base& base); // constructor, putting I's to lowest-energy config
// consistent with Heis_Base configuration for chain RefChain
ODSLF_Ix2_Config (const Heis_Chain& RefChain, const ODSLF_Base& base); // constructor, putting I's to lowest-energy config
// consistent with Heis_Base configuration for chain RefChain
ODSLF_Ix2_Config& operator= (const ODSLF_Ix2_Config& RefConfig);
inline int* operator[] (const int i);
//inline Vect<int> operator[] (const int i);
inline const int* operator[] (const int i) const;
//inline const Vect<int> operator[] (const int i) const;
~ODSLF_Ix2_Config();
};
inline int* ODSLF_Ix2_Config::operator[] (const int i)
//inline Vect<int> Ix2_Config::operator[] (const int i)
{
return Ix2[i];
}
{
return Ix2[i];
}
inline const int* ODSLF_Ix2_Config::operator[] (const int i) const
//inline const Vect<int> Ix2_Config::operator[] (const int i) const
{
return Ix2[i];
}
std::ostream& operator<< (std::ostream& s, const ODSLF_Ix2_Config& RefConfig);
//****************************************************************************
// Objects in class ODSLF_Lambda carry all rapidities of a state
class ODSLF_Lambda {
private:
int Nstrings;
Vect<int> Nrap;
int Nraptot;
DP** lambda;
//Vect<Vect<DP> > lambda;
public:
ODSLF_Lambda ();
ODSLF_Lambda (const Heis_Chain& RefChain, int M); // constructor, puts all lambda's to zero
ODSLF_Lambda (const Heis_Chain& RefChain, const ODSLF_Base& base); // constructor, putting I's to lowest-energy config
ODSLF_Lambda (const Heis_Chain& RefChain, const ODSLF_Base& base); // constructor, putting I's to lowest-energy config
// consistent with Heis_Base configuration for chain RefChain
ODSLF_Lambda& operator= (const ODSLF_Lambda& RefConfig);
inline DP* operator[] (const int i);
//inline Vect<DP> operator[] (const int i);
inline const DP* operator[] (const int i) const;
//inline const Vect<DP> operator[] (const int i) const;
~ODSLF_Lambda();
};
inline DP* ODSLF_Lambda::operator[] (const int i)
//inline Vect<DP> Lambda::operator[] (const int i)
{
return lambda[i];
}
{
return lambda[i];
}
inline const DP* ODSLF_Lambda::operator[] (const int i) const
//inline const Vect<DP> Lambda::operator[] (const int i) const
{
return lambda[i];
}
{
return lambda[i];
}
//****************************************************************************
@@ -168,7 +158,7 @@ namespace JSC {
bool operator>= (const ODSLF_Ix2_Offsets& RefOffsets);
public:
void Set_to_id (long long int idnr);
void Set_to_id (long long int idnr);
void Compute_id ();
void Compute_type_id ();
@@ -178,14 +168,15 @@ namespace JSC {
};
inline long long int ODSLF_Ix2_Offsets_type_id (Vect<int>& nparticles)
{
long long int type_id_here = 0ULL;
{
long long int type_id_here = 0ULL;
for (int i = 0; i < nparticles.size(); ++i)
type_id_here += nparticles[i] * pow_ulli(10ULL, i);
for (int i = 0; i < nparticles.size(); ++i)
type_id_here += nparticles[i] * pow_ulli(10ULL, i);
return(type_id_here);
}
return(type_id_here);
}
//****************************************************************************
// Objects in class ODSLF_Ix2_Offsets_List carry a vector of used Ix2_Offsets
@@ -211,7 +202,7 @@ namespace JSC {
// These contain subclass-specific functions and data.
class ODSLF_Bethe_State {
public:
Heis_Chain chain;
ODSLF_Base base;
@@ -219,7 +210,7 @@ namespace JSC {
ODSLF_Ix2_Config Ix2;
ODSLF_Lambda lambda;
ODSLF_Lambda BE; // Bethe equation for relevant rapidity, in the form BE = theta - (1/N)\sum ... - \pi I/N = 0
DP diffsq; // sum of squares of rapidity differences in last iteration
DP diffsq; // sum of squares of rapidity differences in last iteration
int conv; // convergence status
int iter; // number of iterations necessary for convergence
int iter_Newton; // number of iterations necessary for convergence (Newton method)
@@ -227,8 +218,6 @@ namespace JSC {
int iK; // K = 2.0*PI * iK/Nsites
DP K; // total momentum
DP lnnorm; // ln of norm of reduced Gaudin matrix
//long long int id;
//long long int maxid;
long long int base_id;
long long int type_id;
long long int id;
@@ -236,17 +225,16 @@ namespace JSC {
int nparticles;
public:
ODSLF_Bethe_State ();
ODSLF_Bethe_State ();
ODSLF_Bethe_State (const ODSLF_Bethe_State& RefState); // copy constructor
ODSLF_Bethe_State (const ODSLF_Bethe_State& RefState, long long int type_id_ref); // new state with requested type_id
ODSLF_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
ODSLF_Bethe_State (const Heis_Chain& RefChain, const ODSLF_Base& base); // constructor to lowest-energy config with base
ODSLF_Bethe_State (const Heis_Chain& RefChain, long long int base_id_ref, long long int type_id_ref);
ODSLF_Bethe_State (const Heis_Chain& RefChain, long long int base_id_ref, long long int type_id_ref);
virtual ~ODSLF_Bethe_State () {};
public:
int Charge () { return(base.Mdown); };
//void Set_I_Offset (const I_Offset& RefOffset); // sets the Ix2 to given offsets
int Charge () { return(base.Mdown); };
void Set_Ix2_Offsets (const ODSLF_Ix2_Offsets& RefOffset); // sets the Ix2 to given offsets
void Set_to_id (long long int id_ref);
void Set_to_id (long long int id_ref, ODSLF_Bethe_State& RefState);
@@ -271,65 +259,45 @@ namespace JSC {
// Virtual functions, all defined in the derived classes
public:
virtual void Set_Free_lambdas() { JSCerror("ODSLF_Bethe_State::..."); } // sets the rapidities to solutions of BAEs without scattering terms
virtual bool Check_Admissibility(char option) { JSCerror("ODSLF_Bethe_State::..."); return(false); }
virtual void Set_Free_lambdas() { ABACUSerror("ODSLF_Bethe_State::..."); } // sets the rapidities to solutions of BAEs without scattering terms
virtual bool Check_Admissibility(char option) { ABACUSerror("ODSLF_Bethe_State::..."); return(false); }
// verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
virtual void Compute_BE (int j, int alpha) { JSCerror("ODSLF_Bethe_State::..."); }
virtual void Compute_BE () { JSCerror("ODSLF_Bethe_State::..."); }
virtual DP Iterate_BAE(int i, int alpha) { JSCerror("ODSLF_Bethe_State::..."); return(0.0);}
virtual bool Check_Rapidities() { JSCerror("ODSLF_Bethe_State::..."); return(false); }
virtual void Compute_Energy () { JSCerror("ODSLF_Bethe_State::..."); }
virtual void Build_Reduced_Gaudin_Matrix (SQMat<complex<DP> >& Gaudin_Red) { JSCerror("ODSLF_Bethe_State::..."); }
virtual void Compute_BE (int j, int alpha) { ABACUSerror("ODSLF_Bethe_State::..."); }
virtual void Compute_BE () { ABACUSerror("ODSLF_Bethe_State::..."); }
virtual DP Iterate_BAE(int i, int alpha) { ABACUSerror("ODSLF_Bethe_State::..."); return(0.0);}
virtual bool Check_Rapidities() { ABACUSerror("ODSLF_Bethe_State::..."); return(false); }
virtual void Compute_Energy () { ABACUSerror("ODSLF_Bethe_State::..."); }
virtual void Build_Reduced_Gaudin_Matrix (SQMat<std::complex<DP> >& Gaudin_Red) { ABACUSerror("ODSLF_Bethe_State::..."); }
};
inline bool Force_Descent (char whichDSF, ODSLF_Bethe_State& ScanState, ODSLF_Bethe_State& RefState, int desc_type_required, int iKmod, DP Chem_Pot)
{
JSCerror("Need to implement Force_Descent properly for ODSLF.");
ABACUSerror("Need to implement Force_Descent properly for ODSLF.");
bool force_descent = false;
// Force descent if energy of ScanState is lower than that of RefState
if (ScanState.E - RefState.E - (ScanState.base.Mdown - RefState.base.Mdown) < 0.0) return(true);
/*
// We force descent if
// 1) - there exists a higher string whose quantum number is still on 0
// AND - there is at most a single particle-hole in the 0 base level
// AND - either the particle or the hole hasn't yet moved.
if (RefState.base_id/100000LL > 0) { // there is a higher string
int type0 = RefState.type_id % 10000;
if (type0 == 0
|| type0 == 101 && RefState.offsets.Tableau[0].id * RefState.offsets.Tableau[2].id == 0LL
|| type0 == 110 && RefState.offsets.Tableau[1].id * RefState.offsets.Tableau[2].id == 0LL
|| type0 == 1001 && RefState.offsets.Tableau[0].id * RefState.offsets.Tableau[3].id == 0LL
|| type0 == 1010 && RefState.offsets.Tableau[1].id * RefState.offsets.Tableau[3].id == 0LL) // single p-h pair in base level 0
for (int j = 1; j < RefState.chain.Nstrings; ++j) {
if (RefState.base[j] == 1 && RefState.Ix2[j][0] == 0) {
force_descent = true;
}
}
}
*/
// Force descent if quantum nr distribution is symmetric:
if (RefState.Check_Symmetry()) force_descent = true;
return(force_descent);
}
std::ostream& operator<< (std::ostream& s, const ODSLF_Bethe_State& state);
//****************************************************************************
// Objects in class XXZ_Bethe_State carry all extra information pertaining to XXZ gapless
class ODSLF_XXZ_Bethe_State : public ODSLF_Bethe_State {
public:
ODSLF_Lambda sinhlambda;
ODSLF_Lambda coshlambda;
ODSLF_Lambda tanhlambda;
public:
ODSLF_XXZ_Bethe_State ();
ODSLF_Lambda sinhlambda;
ODSLF_Lambda coshlambda;
ODSLF_Lambda tanhlambda;
public:
ODSLF_XXZ_Bethe_State ();
ODSLF_XXZ_Bethe_State (const ODSLF_XXZ_Bethe_State& RefState); // copy constructor
ODSLF_XXZ_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
ODSLF_XXZ_Bethe_State (const Heis_Chain& RefChain, const ODSLF_Base& base); // constructor to lowest-energy config with base
@@ -337,7 +305,7 @@ namespace JSC {
public:
ODSLF_XXZ_Bethe_State& operator= (const ODSLF_XXZ_Bethe_State& RefState);
public:
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
void Compute_sinhlambda();
@@ -349,14 +317,14 @@ namespace JSC {
DP Iterate_BAE(int i, int j);
bool Check_Rapidities(); // checks that all rapidities are not nan
void Compute_Energy ();
//void Compute_Momentum ();
void Build_Reduced_Gaudin_Matrix (SQMat<complex<DP> >& Gaudin_Red);
void Build_Reduced_Gaudin_Matrix (SQMat<std::complex<DP> >& Gaudin_Red);
// XXZ specific functions:
public:
};
//****************************************************************************
/*
// Objects in class ODSLF_XXX_Bethe_State carry all extra information pertaining to XXX antiferromagnet
@@ -364,29 +332,29 @@ namespace JSC {
class ODSLF_XXX_Bethe_State : public ODSLF_Bethe_State {
public:
ODSLF_XXX_Bethe_State ();
ODSLF_XXX_Bethe_State (const ODSLF_XXX_Bethe_State& RefState); // copy constructor
ODSLF_XXX_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
ODSLF_XXX_Bethe_State (const Heis_Chain& RefChain, const ODSLF__Base& base); // constructor to lowest-energy config with base
ODSLF_XXX_Bethe_State (const Heis_Chain& RefChain, long long int base_id_ref, long long int type_id_ref); // constructor to lowest-energy config with base
ODSLF_XXX_Bethe_State ();
ODSLF_XXX_Bethe_State (const ODSLF_XXX_Bethe_State& RefState); // copy constructor
ODSLF_XXX_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
ODSLF_XXX_Bethe_State (const Heis_Chain& RefChain, const ODSLF__Base& base); // constructor to lowest-energy config with base
ODSLF_XXX_Bethe_State (const Heis_Chain& RefChain, long long int base_id_ref, long long int type_id_ref); // constructor to lowest-energy config with base
public:
ODSLF_XXX_Bethe_State& operator= (const ODSLF_XXX_Bethe_State& RefState);
ODSLF_XXX_Bethe_State& operator= (const ODSLF_XXX_Bethe_State& RefState);
public:
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
bool Check_Admissibility(char option); // verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
void Compute_BE (int j, int alpha);
void Compute_BE ();
DP Iterate_BAE(int i, int j);
bool Check_Rapidities(); // checks that all rapidities are not nan
void Compute_Energy ();
//void Compute_Momentum ();
void Build_Reduced_Gaudin_Matrix (SQMat<complex<DP> >& Gaudin_Red);
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
bool Check_Admissibility(char option); // verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
void Compute_BE (int j, int alpha);
void Compute_BE ();
DP Iterate_BAE(int i, int j);
bool Check_Rapidities(); // checks that all rapidities are not nan
void Compute_Energy ();
//void Compute_Momentum ();
void Build_Reduced_Gaudin_Matrix (SQMat<std::complex<DP> >& Gaudin_Red);
// XXX specific functions
// XXX specific functions
public:
bool Check_Finite_rap ();
bool Check_Finite_rap ();
};
*/
@@ -395,45 +363,45 @@ namespace JSC {
// Objects in class ODSLF_XXZ_gpd_Bethe_State carry all extra information pertaining to XXZ gapped antiferromagnets
class ODSLF_XXZ_gpd_Bethe_State : public ODSLF__Bethe_State {
public:
Lambda sinlambda;
Lambda coslambda;
Lambda tanlambda;
public:
ODSLF_XXZ_gpd_Bethe_State ();
ODSLF_XXZ_gpd_Bethe_State (const ODSLF_XXZ_gpd_Bethe_State& RefState); // copy constructor
ODSLF_XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
ODSLF_XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, const ODSLF_Base& base); // constructor to lowest-energy config with base
ODSLF_XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, long long int base_id_ref, long long int type_id_ref); // constructor to lowest-energy config with base
Lambda sinlambda;
Lambda coslambda;
Lambda tanlambda;
public:
ODSLF_XXZ_gpd_Bethe_State& operator= (const ODSLF_XXZ_gpd_Bethe_State& RefState);
ODSLF_XXZ_gpd_Bethe_State ();
ODSLF_XXZ_gpd_Bethe_State (const ODSLF_XXZ_gpd_Bethe_State& RefState); // copy constructor
ODSLF_XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
ODSLF_XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, const ODSLF_Base& base); // constructor to lowest-energy config with base
ODSLF_XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, long long int base_id_ref, long long int type_id_ref); // constructor to lowest-energy config with base
public:
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
void Compute_sinlambda();
void Compute_coslambda();
void Compute_tanlambda();
int Weight(); // weight function for contributions cutoff
bool Check_Admissibility(char option); // verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
void Compute_BE (int j, int alpha);
void Compute_BE ();
DP Iterate_BAE(int i, int j);
void Iterate_BAE_Newton();
bool Check_Rapidities(); // checks that all rapidities are not nan and are in interval ]-PI/2, PI/2]
void Compute_Energy ();
//void Compute_Momentum ();
void Build_Reduced_Gaudin_Matrix (SQMat<complex<DP> >& Gaudin_Red);
ODSLF_XXZ_gpd_Bethe_State& operator= (const ODSLF_XXZ_gpd_Bethe_State& RefState);
// XXZ_gpd specific functions
public:
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
void Compute_sinlambda();
void Compute_coslambda();
void Compute_tanlambda();
int Weight(); // weight function for contributions cutoff
bool Check_Admissibility(char option); // verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
void Compute_BE (int j, int alpha);
void Compute_BE ();
DP Iterate_BAE(int i, int j);
void Iterate_BAE_Newton();
bool Check_Rapidities(); // checks that all rapidities are not nan and are in interval ]-PI/2, PI/2]
void Compute_Energy ();
//void Compute_Momentum ();
void Build_Reduced_Gaudin_Matrix (SQMat<std::complex<DP> >& Gaudin_Red);
// XXZ_gpd specific functions
public:
};
*/
//***********************************************
// Function declarations
/*
// in M_vs_H.cc
@@ -445,19 +413,16 @@ namespace JSC {
DP X_avg (char xyorz, DP Delta, int N, int M);
*/
DP Chemical_Potential (const ODSLF_Bethe_State& RefState);
//DP Sumrule_Factor (char whichDSF, Heis_Bethe_State& RefState, DP Chem_Pot, bool fixed_iK, int iKneeded);
DP Sumrule_Factor (char whichDSF, ODSLF_Bethe_State& RefState, DP Chem_Pot, int iKmin, int iKmax);
void Evaluate_F_Sumrule (string prefix, char whichDSF, const ODSLF_Bethe_State& RefState, DP Chem_Pot, int iKmin, int iKmax);
void Evaluate_F_Sumrule (std::string prefix, char whichDSF, const ODSLF_Bethe_State& RefState, DP Chem_Pot, int iKmin, int iKmax);
complex<DP> ln_Sz_ME (ODSLF_XXZ_Bethe_State& A, ODSLF_XXZ_Bethe_State& B);
complex<DP> ln_Smin_ME (ODSLF_XXZ_Bethe_State& A, ODSLF_XXZ_Bethe_State& B);
std::complex<DP> ln_Sz_ME (ODSLF_XXZ_Bethe_State& A, ODSLF_XXZ_Bethe_State& B);
std::complex<DP> ln_Smin_ME (ODSLF_XXZ_Bethe_State& A, ODSLF_XXZ_Bethe_State& B);
//DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, ODSLF_XXZ_Bethe_State& LeftState,
// ODSLF_XXZ_Bethe_State& RefState, DP Chem_Pot, fstream& DAT_outfile);
DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, ODSLF_XXZ_Bethe_State& LeftState,
ODSLF_XXZ_Bethe_State& RefState, DP Chem_Pot, stringstream& DAT_outfile);
DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, ODSLF_XXZ_Bethe_State& LeftState,
ODSLF_XXZ_Bethe_State& RefState, DP Chem_Pot, std::stringstream& DAT_outfile);
} // namespace JSC
} // namespace ABACUS
#endif
+828
View File
@@ -0,0 +1,828 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: ABACUS_Scan.h
Purpose: Declares all classes and functions used in the
ABACUS logic of scanning with threads.
***********************************************************/
#ifndef ABACUS_SCAN_H
#define ABACUS_SCAN_H
#include "ABACUS.h"
namespace ABACUS {
const int MAX_STATE_LIST_SIZE = 10000;
// Functions in src/UTILS/Data_File_Name.cc:
void Data_File_Name (std::stringstream& name, char whichDSF, DP c_int, DP L, int N,
int iKmin, int iKmax, DP kBT, DP L2, std::string defaultname);
void Data_File_Name (std::stringstream& name, char whichDSF, int iKmin, int iKmax, DP kBT,
LiebLin_Bethe_State& State, LiebLin_Bethe_State& RefScanState, std::string defaultname);
void Data_File_Name (std::stringstream& name, char whichDSF, DP Delta, int N, int M, int iKmin, int iKmax,
DP kBT, int N2, std::string defaultname);
void Data_File_Name (std::stringstream& name, char whichDSF, int iKmin, int iKmax, DP kBT,
Heis_Bethe_State& State, Heis_Bethe_State& RefScanState, std::string defaultname);
void ODSLF_Data_File_Name (std::stringstream& name, char whichDSF, DP Delta, int N, int M,
int iKmin, int iKmax, DP kBT, int N2, std::string defaultname);
void Data_File_Name (std::stringstream& name, char whichDSF, int iKmin, int iKmax, DP kBT,
ODSLF_Bethe_State& State, ODSLF_Bethe_State& RefScanState, std::string defaultname);
// Coding to convert ints to strings: for application in reduced labels
//const int ABACUScodingsize = 64; // use a multiple of 2 to accelerate divisions in labeling.
//const char ABACUScoding[] = {'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z', 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '!', '?'};
// From ABACUS++T_8 onwards: forbid special characters as |, :, !, ? and all capital letters in labels.
// This is due to the dumb capitalization-preserving but capitalization-insensitive HFS+ filesystem on Mac OS X.
const int ABACUScodingsize = 32;
const char ABACUScoding[] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v'};
const char LABELSEP = '_'; // was _
const char TYPESEP = 'x'; // was |
const char EXCSEP = 'y'; // was :
const char INEXCSEP = 'z'; // was @
struct State_Label_Data {
Vect<int> type; // integer type labels of the types present
Vect<int> M; // how many particles of each type
Vect<int> nexc; // how many excitations as compared to the reference state used
Vect<Vect<int> > Ix2old; // which Ix2 will be excited
Vect<Vect<int> > Ix2exc; // which Ix2 the excitation has shifted to
State_Label_Data (const Vect<int>& type_ref, const Vect<int>& M_ref,
const Vect<int>& nexc_ref, const Vect<Vect<int> >& Ix2old_ref, const Vect<Vect<int> >& Ix2exc_ref)
{
type = type_ref; M = M_ref; nexc = nexc_ref; Ix2old = Ix2old_ref; Ix2exc = Ix2exc_ref;
}
};
std::string Extract_Base_Label (std::string label); // works for labels and complabels
std::string Extract_nexc_Label (std::string label);
// For compressed labels: conversions between integers and char/strings.
std::string Convert_POSINT_to_STR (int int_to_convert);
int Convert_CHAR_to_POSINT (char char_to_convert);
int Convert_STR_to_POSINT (std::string str_to_convert);
State_Label_Data Read_Base_Label (std::string label);
State_Label_Data Read_State_Label (std::string label, const Vect<Vect<int> >& OriginIx2);
State_Label_Data Read_State_Label (std::string label, const Vect<int>& OriginIx2); // if there is only one type
std::string Return_State_Label (State_Label_Data data, const Vect<Vect<int> >& OriginIx2);
std::string Return_State_Label (State_Label_Data data, const Vect<int>& OriginIx2); // if there is only one type
std::string Return_State_Label (const Vect<Vect<int> >& ScanIx2, const Vect<Vect<int> >& OriginIx2);
std::string Return_State_Label (const Vect<int>& ScanIx2, const Vect<int>& OriginIx2); // if there is only one type
Vect<Vect<int> > Return_Ix2_from_Label (std::string label_ref, const Vect<Vect<int> >& OriginIx2);
Vect<int> Return_Ix2_from_Label (std::string label_ref, const Vect<int>& OriginIx2); // specialization to Lieb-Liniger
// Functions for descending states: in SCAN/Descendents.cc
Vect<std::string> Descendent_States_with_iK_Stepped_Up (std::string ScanIx2_label, const LiebLin_Bethe_State& OriginState, bool disperse_only_current_exc, bool preserve_nexc);
Vect<std::string> Descendent_States_with_iK_Stepped_Down (std::string ScanIx2_label, const LiebLin_Bethe_State& OriginState, bool disperse_only_current_exc, bool preserve_nexc);
Vect<std::string> Descendent_States_with_iK_Preserved (std::string ScanIx2_label, const LiebLin_Bethe_State& OriginState, bool disperse_only_current_exc_up, bool preserve_nexc_up, bool disperse_only_current_exc_down, bool preserve_nexc_down);
Vect<std::string> Descendent_States_with_iK_Stepped_Up (std::string ScanIx2_label, const Heis_Bethe_State& OriginState, bool disperse_only_current_exc, bool preserve_nexc);
Vect<std::string> Descendent_States_with_iK_Stepped_Down (std::string ScanIx2_label, const Heis_Bethe_State& OriginState, bool disperse_only_current_exc, bool preserve_nexc);
Vect<std::string> Descendent_States_with_iK_Preserved (std::string ScanIx2_label, const Heis_Bethe_State& OriginState, bool disperse_only_current_exc_up, bool preserve_nexc_up, bool disperse_only_current_exc_down, bool preserve_nexc_down);
// For symmetric state scanning:
Vect<std::string> Descendent_States_with_iK_Stepped_Up_rightIx2only
(std::string ScanIx2_label, const LiebLin_Bethe_State& OriginState, bool disperse_only_current_exc, bool preserve_nexc);
Vect<std::string> Descendent_States_with_iK_Stepped_Down_rightIx2only
(std::string ScanIx2_label, const LiebLin_Bethe_State& OriginState, bool disperse_only_current_exc, bool preserve_nexc);
Vect<std::string> Descendent_States_with_iK_Stepped_Up_rightIx2only
(std::string ScanIx2_label, const Heis_Bethe_State& OriginState, bool disperse_only_current_exc, bool preserve_nexc);
Vect<std::string> Descendent_States_with_iK_Stepped_Down_rightIx2only
(std::string ScanIx2_label, const Heis_Bethe_State& OriginState, bool disperse_only_current_exc, bool preserve_nexc);
// Functions in src/SCAN/General_Scan.cc:
void Scan_LiebLin (char whichDSF, DP c_int, DP L, int N, int iKmin, int iKmax, DP kBT,
int Max_Secs, DP target_sumrule, bool refine, int paralevel, Vect<int> rank, Vect<int> nr_processors);
void Scan_LiebLin (char whichDSF, DP c_int, DP L, int N, int iKmin, int iKmax, DP kBT,
int Max_Secs, DP target_sumrule, bool refine);
void Scan_LiebLin (char whichDSF, LiebLin_Bethe_State AveragingState, std::string defaultScanStatename, int iKmin, int iKmax,
int Max_Secs, DP target_sumrule, bool refine, int paralevel, Vect<int> rank, Vect<int> nr_processors);
void Scan_LiebLin (char whichDSF, LiebLin_Bethe_State AveragingState, std::string defaultname, int iKmin, int iKmax,
int Max_Secs, DP target_sumrule, bool refine);
void Scan_LiebLin_Geometric_Quench (DP c_int, DP L_1, int type_id_1, long long int id_1, DP L_2, int N,
int iK_UL, int Max_Secs, DP target_sumrule, bool refine);
void Scan_Heis (char whichDSF, DP Delta, int N, int M, int iKmin, int iKmax,
int Max_Secs, DP target_sumrule, bool refine, int paralevel, Vect<int> rank, Vect<int> nr_processors);
void Scan_Heis (char whichDSF, DP Delta, int N, int M, int iKmin, int iKmax,
int Max_Secs, DP target_sumrule, bool refine);
void Scan_Heis (char whichDSF, XXZ_Bethe_State& AveragingState, std::string defaultScanStatename, int iKmin, int iKmax,
int Max_Secs, DP target_sumrule, bool refine, int paralevel, Vect<int> rank, Vect<int> nr_processors);
void Scan_Heis (char whichDSF, XXX_Bethe_State& AveragingState, std::string defaultScanStatename, int iKmin, int iKmax,
int Max_Secs, DP target_sumrule, bool refine, int paralevel, Vect<int> rank, Vect<int> nr_processors);
void Scan_Heis (char whichDSF, XXZ_gpd_Bethe_State& AveragingState, std::string defaultScanStatename, int iKmin, int iKmax,
int Max_Secs, DP target_sumrule, bool refine, int paralevel, Vect<int> rank, Vect<int> nr_processors);
void Scan_ODSLF (char whichDSF, DP Delta, int N, int M, int iKmin, int iKmax,
int Max_Secs, DP target_sumrule, bool refine, int rank, int nr_processors);
void Scan_ODSLF (char whichDSF, DP Delta, int N, int M, int iKmin, int iKmax, int Max_Secs, bool refine);
void Scan_ODSLF (char whichDSF, DP Delta, int N, int M, int iKneeded, int Max_Secs, bool refine);
void Scan_ODSLF (char whichDSF, DP Delta, int N, int M, int Max_Secs, bool refine);
// Functions to prepare and wrapup parallel scans:
void Prepare_Parallel_Scan_LiebLin (char whichDSF, DP c_int, DP L, int N, int iKmin, int iKmax, DP kBT,
std::string defaultname, int paralevel, Vect<int> rank_lower_paralevels,
Vect<int> nr_processors_lower_paralevels, int nr_processors_at_newlevel);
void Wrapup_Parallel_Scan_LiebLin (char whichDSF, DP c_int, DP L, int N, int iKmin, int iKmax, DP kBT,
std::string defaultname, int paralevel, Vect<int> rank_lower_paralevels,
Vect<int> nr_processors_lower_paralevels, int nr_processors_at_newlevel);
void Prepare_Parallel_Scan_Heis (char whichDSF, DP Delta, int N, int M, int iKmin, int iKmax,
int paralevel, Vect<int> rank_lower_paralevels,
Vect<int> nr_processors_lower_paralevels, int nr_processors_at_newlevel);
void Wrapup_Parallel_Scan_Heis (char whichDSF, DP Delta, int N, int M, int iKmin, int iKmax,
int paralevel, Vect<int> rank_lower_paralevels,
Vect<int> nr_processors_lower_paralevels, int nr_processors_at_newlevel);
void Sort_RAW_File (const char ffsq_file[], char optionchar);
void Sort_RAW_File (const char ffsq_file[], char optionchar, char whichDSF);
// Functions for data interpretation:
DP Smoothen_RAW_into_SF (std::string prefix, int iKmin, int iKmax, int DiK,
DP ommin, DP ommax, int Nom, DP gwidth, DP normalization, DP denom_sum_K);
DP Smoothen_RAW_into_SF (std::string prefix, Vect<std::string> rawfilename, Vect<DP> weight, int iKmin, int iKmax, int DiK,
DP ommin, DP ommax, int Nom, DP gwidth, DP normalization, DP denom_sum_K);
void Write_K_File (DP Length, int iKmin, int iKmax);
void Write_Omega_File (int Nout_omega, DP omegamin, DP omegamax);
// Smoothen with gaussian width scaled with two-particle bandwidth
DP Smoothen_RAW_into_SF_LiebLin_Scaled (std::string prefix, DP L, int N, int iKmin, int iKmax, int DiK, DP ommin, DP ommax, int Nom, DP width, DP normalization);
//****************************************************************************
struct Scan_Info {
DP sumrule_obtained;
DP Nfull; // dimensionality of (sub)Hilbert space considered
long long int Ninadm;
long long int Ndata;
long long int Ndata_conv;
long long int Ndata_conv0;
double TT; // total computation time in seconds
public:
Scan_Info(); // constructor, puts everything to zero
Scan_Info (DP sr, DP Nf, long long int Ni, long long int Nd, long long int Ndc, long long int Ndc0, double t);
void Save (const char* outfile_Cstr);
void Load (const char* infile_Cstr);
inline Scan_Info& operator = (const Scan_Info& ref_info)
{
sumrule_obtained = ref_info.sumrule_obtained;
Nfull = ref_info.Nfull;
Ninadm = ref_info.Ninadm;
Ndata = ref_info.Ndata;
Ndata_conv = ref_info.Ndata_conv;
Ndata_conv0 = ref_info.Ndata_conv0;
TT = ref_info.TT;
return(*this);
}
inline Scan_Info& operator+= (const Scan_Info& ref_info)
{
if (this != &ref_info) {
sumrule_obtained += ref_info.sumrule_obtained;
Nfull += ref_info.Nfull;
Ninadm += ref_info.Ninadm;
Ndata += ref_info.Ndata;
Ndata_conv += ref_info.Ndata_conv;
Ndata_conv0 += ref_info.Ndata_conv0;
TT += ref_info.TT;
}
return(*this);
}
inline Scan_Info& operator-= (const Scan_Info& ref_info)
{
if (this != &ref_info) {
sumrule_obtained -= ref_info.sumrule_obtained;
Nfull -= ref_info.Nfull;
Ninadm -= ref_info.Ninadm;
Ndata -= ref_info.Ndata;
Ndata_conv -= ref_info.Ndata_conv;
Ndata_conv0 -= ref_info.Ndata_conv0;
TT -= ref_info.TT;
}
return(*this);
}
};
std::ostream& operator<< (std::ostream& s, const Scan_Info& info);
template<class Tstate>
Scan_Info General_Scan (char whichDSF, int iKmin, int iKmax, int iKmod, DP kBT, Tstate& AveragingState, Tstate& SeedScanState,
std::string defaultScanStatename, int Max_Secs, DP target_sumrule, bool refine, int paralevel, Vect<int> rank, Vect<int> nr_processors);
//****************************************************************************
// Functions in src/SCAN/Descendents.cc:
Vect<std::string> Descendents (const LiebLin_Bethe_State& ScanState, const LiebLin_Bethe_State& OriginState, int type_required);
Vect<std::string> Descendents (const Heis_Bethe_State& ScanState, const Heis_Bethe_State& OriginState, int type_required);
struct Scan_Thread {
std::string label;
int type;
Scan_Thread ();
Scan_Thread (std::string label_ref, int type_ref) {
label = label_ref;
type = type_ref;
}
Scan_Thread& operator= (const Scan_Thread& RefThread);
};
struct Scan_Thread_Data {
// By convention, a Scan_Thread_Data object handles a list of threads which are yet to be descended.
// Improvement on Scan_Thread_Set used up to ABACUS++G_7, saving data to disk instead of holding it in memory.
int nlists = 6400; // number of threads lists, fixed to this number by convention.
DP logscale = (1.0/64) * log(2.0); // each separate list contains threads differing by a scale factor of 2^{1/64} \approx 1.01.
std::string thrdir_name; // directory in which threads files are saved.
Vect<int> nthreads_total;
Vect<int> nthreads_on_disk;
int lowest_il_with_nthreads_neq_0;
// In-memory storage, for adding threads efficiently without constantly writing to disk
// These objects are saved to disk when Next_Scan_Threads are called.
Vect<int> dim;
Vect<int> nthreads_in_memory;
Vect<Vect<std::string> > label;
Vect<Vect<int> > type; // which type of descendent is needed
Vect<std::string> filename;
Scan_Thread_Data ();
Scan_Thread_Data (std::string thrdir_name_ref, bool refine);
~Scan_Thread_Data ();
bool Increase_Memory_Size (int il, int nr_to_add);
void Include_Thread (DP abs_data_value_ref, std::string label_ref, int type_ref);
void Include_Thread (int il, std::string label_ref, int type_ref);
Vect<Scan_Thread> Extract_Next_Scan_Threads (); // returns a vector of the threads that are next in line. By defn, all threads with index il == lowest_il_with_nthreads_neq_0. These are removed from the object.
Vect<Scan_Thread> Extract_Next_Scan_Threads (int min_nr); // as above, but returns a minimum of min_nr threads.
void Flush_to_Disk (int il);
void Save ();
void Load ();
};
//****************************************************************************
// To populate a list of states for scanning:
inline void Scan_for_Possible_Bases (const Vect<int> SeedNrap, const Vect<int> Str_L,
int Mdown_remaining, Vect<std::string>& possible_base_label, int& nfound, int nexc_max_used,
int base_level_to_scan, Vect<int>& Nrapidities)
{
if (Mdown_remaining < 0) { ABACUSerror("Scan_for_Possible_Bases: shouldn't be here..."); } // reached inconsistent point
if (base_level_to_scan == 0) {
if (Str_L[0] != 1) ABACUSerror("Str_L[0] != 1 in ABACUS_Scan.h Scan_for_Possible_Bases.");
Nrapidities[0] = Mdown_remaining;
// Set label:
std::stringstream M0out;
M0out << Nrapidities[0];
possible_base_label[nfound] = M0out.str();
for (int itype = 1; itype < Nrapidities.size(); ++itype)
if (Nrapidities[itype] > 0) {
possible_base_label[nfound] += TYPESEP;
std::stringstream typeout;
typeout << itype;
possible_base_label[nfound] += typeout.str();
possible_base_label[nfound] += EXCSEP;
std::stringstream Mout;
Mout << Nrapidities[itype];
possible_base_label[nfound] += Mout.str();
}
nfound++;
}
else {
// Preserve the number of strings at this level as compared to SeedState:
Nrapidities[base_level_to_scan] = SeedNrap[base_level_to_scan];
if (Mdown_remaining - Str_L[base_level_to_scan] * Nrapidities[base_level_to_scan] >= 0)
Scan_for_Possible_Bases (SeedNrap, Str_L, Mdown_remaining - Str_L[base_level_to_scan] * Nrapidities[base_level_to_scan],
possible_base_label, nfound, nexc_max_used, base_level_to_scan - 1, Nrapidities);
// Reduce number of strings at this level as compared to SeedState:
for (int i = 1; i <= ABACUS::min(SeedNrap[base_level_to_scan], nexc_max_used/Str_L[base_level_to_scan]); ++i) {
Nrapidities[base_level_to_scan] = SeedNrap[base_level_to_scan] - i;
if (Mdown_remaining - Str_L[base_level_to_scan] * Nrapidities[base_level_to_scan] >= 0)
Scan_for_Possible_Bases (SeedNrap, Str_L, Mdown_remaining - Str_L[base_level_to_scan] * Nrapidities[base_level_to_scan],
possible_base_label, nfound, nexc_max_used - i*Str_L[base_level_to_scan], base_level_to_scan - 1, Nrapidities);
}
// Increase the number of strings at this level as compared to SeedState:
for (int i = 1; i <= ABACUS::min(Mdown_remaining/Str_L[base_level_to_scan], nexc_max_used/Str_L[base_level_to_scan]); ++i) {
Nrapidities[base_level_to_scan] = SeedNrap[base_level_to_scan] + i;
if (Mdown_remaining - Str_L[base_level_to_scan] * Nrapidities[base_level_to_scan] >= 0)
Scan_for_Possible_Bases (SeedNrap, Str_L, Mdown_remaining - Str_L[base_level_to_scan] * Nrapidities[base_level_to_scan],
possible_base_label, nfound, nexc_max_used - i*Str_L[base_level_to_scan], base_level_to_scan - 1, Nrapidities);
}
}
}
inline Vect<std::string> Possible_Bases (const Vect<int> SeedNrap, const Vect<int> Str_L, int Mdown)//const Heis_Bethe_State& SeedState)
{
int nexc_max_used = NEXC_MAX_HEIS;
Vect<std::string> possible_base_label (1000);
int nfound = 0;
Vect<int> Nrapidities = SeedNrap;
int Mdown_remaining = Mdown;
Scan_for_Possible_Bases (SeedNrap, Str_L, Mdown_remaining, possible_base_label, nfound, nexc_max_used, SeedNrap.size() - 1, Nrapidities);
// Copy results into a clean vector:
Vect<std::string> possible_base_label_found (nfound);
for (int i = 0; i < nfound; ++i) possible_base_label_found[i] = possible_base_label[i];
return(possible_base_label_found);
}
//****************************************************************************
template<class Tstate>
class Scan_State_List {
public:
int ndef;
Vect<Tstate> State;
Vect<std::string> base_label;
Vect<Scan_Info> info; // info for base and type of State[n]
Vect<bool> flag_for_scan; // set to true, next round of scanning will use this base/type
Vect<bool> scan_attempted; // whether this has already been attempted
public:
inline Scan_State_List (char whichDSF, const Tstate& SeedScanState);
public:
inline Tstate& Return_State (std::string base_label_ref); // returns a state corresponding to same base and type
inline void Populate_List (char whichDSF, const Tstate& SeedScanState); // creates all types of states containing up to nexc_max excitations
inline void Include_Info (Scan_Info& info_to_add, std::string base_label_ref);
inline void Raise_Scanning_Flags (DP threshold); // checks whether base/type should be scanned based on simpler base/type combinations
inline void Order_in_SRC ();
inline void Save_Info (const char* sumfile_Cstr);
inline void Load_Info (const char* sumfile_Cstr);
};
// Do the explicit class specializations:
template<>
inline Scan_State_List<LiebLin_Bethe_State>::Scan_State_List (char whichDSF, const LiebLin_Bethe_State& SeedScanState)
: ndef(0), State(Vect<LiebLin_Bethe_State>(MAX_STATE_LIST_SIZE)), base_label(Vect<std::string>(MAX_STATE_LIST_SIZE)),
info(Vect<Scan_Info>(MAX_STATE_LIST_SIZE)), flag_for_scan(Vect<bool>(false, MAX_STATE_LIST_SIZE)),
scan_attempted(Vect<bool>(false, MAX_STATE_LIST_SIZE))
{
State[0] = SeedScanState;
}
template<>
inline Scan_State_List<XXZ_Bethe_State>::Scan_State_List (char whichDSF, const XXZ_Bethe_State& SeedScanState)
: ndef(0), State(Vect<XXZ_Bethe_State>(MAX_STATE_LIST_SIZE)), base_label(Vect<std::string>(MAX_STATE_LIST_SIZE)),
info(Vect<Scan_Info>(MAX_STATE_LIST_SIZE)), flag_for_scan(Vect<bool>(false, MAX_STATE_LIST_SIZE)),
scan_attempted(Vect<bool>(false, MAX_STATE_LIST_SIZE))
{
State[0] = SeedScanState;
}
template<>
inline Scan_State_List<XXX_Bethe_State>::Scan_State_List (char whichDSF, const XXX_Bethe_State& SeedScanState)
: ndef(0), State(Vect<XXX_Bethe_State>(MAX_STATE_LIST_SIZE)), base_label(Vect<std::string>(MAX_STATE_LIST_SIZE)),
info(Vect<Scan_Info>(MAX_STATE_LIST_SIZE)), flag_for_scan(Vect<bool>(false, MAX_STATE_LIST_SIZE)),
scan_attempted(Vect<bool>(false, MAX_STATE_LIST_SIZE))
{
State[0] = SeedScanState;
}
template<>
inline Scan_State_List<XXZ_gpd_Bethe_State>::Scan_State_List (char whichDSF, const XXZ_gpd_Bethe_State& SeedScanState)
: ndef(0), State(Vect<XXZ_gpd_Bethe_State>(MAX_STATE_LIST_SIZE)), base_label(Vect<std::string>(MAX_STATE_LIST_SIZE)),
info(Vect<Scan_Info>(MAX_STATE_LIST_SIZE)), flag_for_scan(Vect<bool>(false, MAX_STATE_LIST_SIZE)),
scan_attempted(Vect<bool>(false, MAX_STATE_LIST_SIZE))
{
State[0] = SeedScanState;
}
/* IN_DEVELOPMENT
template<>
inline Scan_State_List<ODSLF_XXZ_Bethe_State>::Scan_State_List (char whichDSF, const ODSLF_XXZ_Bethe_State& RefState)
: ndef(0), State(Vect<ODSLF_XXZ_Bethe_State>(MAX_STATE_LIST_SIZE)), base_label(Vect<std::string>(MAX_STATE_LIST_SIZE)),
info(Vect<Scan_Info>(MAX_STATE_LIST_SIZE)), flag_for_scan(Vect<bool>(false, MAX_STATE_LIST_SIZE)),
scan_attempted(Vect<bool>(false, MAX_STATE_LIST_SIZE))
{
if (whichDSF == 'Z' || whichDSF == 'z') State[0] = ODSLF_XXZ_Bethe_State(RefState.chain, RefState.base.Mdown);
else if (whichDSF == 'm') State[0] = ODSLF_XXZ_Bethe_State(RefState.chain, RefState.base.Mdown - 1);
else if (whichDSF == 'p') State[0] = ODSLF_XXZ_Bethe_State(RefState.chain, RefState.base.Mdown + 1);
else ABACUSerror("Unknown whichDSF in Scan_State_List<ODSLF_XXZ... constructor.");
}
*/
template<>
inline LiebLin_Bethe_State& Scan_State_List<LiebLin_Bethe_State>::Return_State (std::string base_label_ref)
{
int n = 0;
while (n < ndef && base_label_ref.compare(base_label[n]) != 0) n++;
if (n == ndef) {
State[n] = State[0];
base_label[n] = base_label_ref;
info[n].Nfull = 1LL; // Nfull not definable for LiebLin
ndef++;
}
return(State[n]);
}
template<>
inline XXZ_Bethe_State& Scan_State_List<XXZ_Bethe_State>::Return_State (std::string base_label_ref)
{
int n = 0;
while (n < ndef && base_label_ref.compare(base_label[n]) != 0) n++;
if (n == ndef) {
Heis_Base checkbase (State[0].chain, base_label_ref);
State[n] = XXZ_Bethe_State (State[0].chain, checkbase);
info[n].Nfull = checkbase.dimH;
ndef++;
}
return(State[n]);
}
template<>
inline XXX_Bethe_State& Scan_State_List<XXX_Bethe_State>::Return_State (std::string base_label_ref)
{
int n = 0;
while (n < ndef && base_label_ref.compare(base_label[n]) != 0) n++;
if (n == ndef) {
Heis_Base checkbase (State[0].chain, base_label_ref);
State[n] = XXX_Bethe_State (State[0].chain, checkbase);
info[n].Nfull = checkbase.dimH;
ndef++;
}
return(State[n]);
}
template<>
inline XXZ_gpd_Bethe_State& Scan_State_List<XXZ_gpd_Bethe_State>::Return_State (std::string base_label_ref)
{
int n = 0;
while (n < ndef && base_label_ref.compare(base_label[n]) != 0) n++;
if (n == ndef) {
Heis_Base checkbase (State[0].chain, base_label_ref);
State[n] = XXZ_gpd_Bethe_State (State[0].chain, checkbase);
info[n].Nfull = checkbase.dimH;
ndef++;
}
return(State[n]);
}
/* IN DEVELOPMENT
template<>
inline ODSLF_XXZ_Bethe_State& Scan_State_List<ODSLF_XXZ_Bethe_State>::Return_State (long long int base_id_ref, long long int type_id_ref)
{
int n = 0;
while (n < ndef && !(base_id_ref == State[n].base_id && type_id_ref == State[n].type_id)) n++;
if (n == ndef) {
State[n] = ODSLF_XXZ_Bethe_State (State[0].chain, base_id_ref, type_id_ref);
info[n].Nfull = State[n].maxid + 1LL;
ndef++;
}
return(State[n]);
}
*/
template<>
inline void Scan_State_List<LiebLin_Bethe_State>::Populate_List (char whichDSF, const LiebLin_Bethe_State& SeedScanState)
{
// For LiebLin_Bethe_State: only one base is used, so there is only one state here.
if (ndef != 0) ABACUSerror("Please only populate a virgin Scan_State_List.");
std::stringstream baselabel;
baselabel << State[0].N;
base_label[0] = baselabel.str();
std::stringstream label0;
label0 << State[0].N << LABELSEP << ABACUScoding[0] << LABELSEP;//"_0_";
State[0].Set_to_Label (label0.str(), SeedScanState.Ix2);
info[0].Nfull = 1LL; // Nfull not definable for LiebLin
ndef = 1;
}
template<>
inline void Scan_State_List<XXZ_Bethe_State>::Populate_List (char whichDSF, const XXZ_Bethe_State& SeedScanState)
{
// creates all types of states containing up to nexc_max excitations
if (ndef != 0) ABACUSerror("Please only populate a virgin Scan_State_List.");
// We assume that SeedScanState has quantum numbers which are set according to the relevant AveragingState.
// This function creates a list of states with other bases in the vicinity of that of SeedScanState,
// matching the quantum numbers as closely as possible.
Vect<int> Str_L(SeedScanState.chain.Nstrings);
for (int i = 0; i < SeedScanState.chain.Nstrings; ++i) Str_L[i] = SeedScanState.chain.Str_L[i];
// First of all, we create a list of the possible bases themselves.
Vect<std::string> bases_label = Possible_Bases (SeedScanState.base.Nrap, Str_L, SeedScanState.base.Mdown); // returns a vector of possible bases
for (int ib = 0; ib < bases_label.size(); ++ib) {
Heis_Base checkbase (State[0].chain, bases_label[ib]);
State[ndef] = XXZ_Bethe_State (State[0].chain, checkbase);
State[ndef].Set_to_Closest_Matching_Ix2_fixed_Base (SeedScanState);
State[ndef].Set_Label_from_Ix2 (State[ndef].Ix2); // sets to trivial label for this base
base_label[ndef] = bases_label[ib];
info[ndef].Nfull = State[ndef].base.dimH;
ndef++;
if (ndef >= MAX_STATE_LIST_SIZE) ABACUSerror("Increase number of elements in ScanStateList.");
}
}
template<>
inline void Scan_State_List<XXX_Bethe_State>::Populate_List (char whichDSF, const XXX_Bethe_State& SeedScanState)
{
// creates all types of states containing up to nexc_max excitations
if (ndef != 0) ABACUSerror("Please only populate a virgin Scan_State_List.");
// We assume that SeedScanState has quantum numbers which are set according to the relevant AveragingState.
// This function creates a list of states with other bases in the vicinity of that of SeedScanState,
// matching the quantum numbers as closely as possible.
Vect<int> Str_L(SeedScanState.chain.Nstrings);
for (int i = 0; i < SeedScanState.chain.Nstrings; ++i) Str_L[i] = SeedScanState.chain.Str_L[i];
// To take infinite rapidities into account, we use intermediate states with up to 2 less finite rapidities (1 for Szz, 2 for Spm)
int nrinfrapmax = 0;
if (whichDSF == 'z') nrinfrapmax = 1;
else if (whichDSF == 'p') nrinfrapmax = ABACUS::min(2, SeedScanState.base.Mdown);
Vect<int> Nrapmod = SeedScanState.base.Nrap;
for (int nrinfrap = 0; nrinfrap <= nrinfrapmax; ++nrinfrap) {
Nrapmod[0] = SeedScanState.base.Nrap[0] - nrinfrap;
if (Nrapmod[0] < 0) ABACUSerror("Putting too many rapidities at infinity in ABACUS_Scan.h: Possible_Bases.");
Vect<std::string> bases_label = Possible_Bases (Nrapmod, Str_L, SeedScanState.base.Mdown-nrinfrap); // returns a vector of possible bases
for (int ib = 0; ib < bases_label.size(); ++ib) {
Heis_Base checkbase (State[0].chain, bases_label[ib]);
State[ndef] = XXX_Bethe_State (State[0].chain, checkbase);
State[ndef].Set_to_Closest_Matching_Ix2_fixed_Base (SeedScanState);
base_label[ndef] = bases_label[ib];
info[ndef].Nfull = State[ndef].base.dimH;
ndef++;
if (ndef >= MAX_STATE_LIST_SIZE) ABACUSerror("Increase number of elements in ScanStateList.");
}
} // for nrinfrap
}
template<>
inline void Scan_State_List<XXZ_gpd_Bethe_State>::Populate_List (char whichDSF, const XXZ_gpd_Bethe_State& SeedScanState)
{
// creates all types of states containing up to nexc_max excitations
if (ndef != 0) ABACUSerror("Please only populate a virgin Scan_State_List.");
// We assume that SeedScanState has quantum numbers which are set according to the relevant AveragingState.
// This function creates a list of states with other bases in the vicinity of that of SeedScanState,
// matching the quantum numbers as closely as possible.
Vect<int> Str_L(SeedScanState.chain.Nstrings);
for (int i = 0; i < SeedScanState.chain.Nstrings; ++i) Str_L[i] = SeedScanState.chain.Str_L[i];
// First of all, we create a list of the possible bases themselves.
Vect<std::string> bases_label = Possible_Bases (SeedScanState.base.Nrap, Str_L, SeedScanState.base.Mdown); // returns a vector of possible bases
for (int ib = 0; ib < bases_label.size(); ++ib) {
Heis_Base checkbase (State[0].chain, bases_label[ib]);
State[ndef] = XXZ_gpd_Bethe_State (State[0].chain, checkbase);
State[ndef].Set_to_Closest_Matching_Ix2_fixed_Base (SeedScanState);
base_label[ndef] = bases_label[ib];
info[ndef].Nfull = State[ndef].base.dimH;
ndef++;
if (ndef >= MAX_STATE_LIST_SIZE) ABACUSerror("Increase number of elements in ScanStateList.");
}
}
/* IN DEVELOPMENT
template<>
inline void Scan_State_List<ODSLF_XXZ_Bethe_State>::Populate_List ()
{
// creates all types of states containing up to nexc_max excitations
if (ndef != 0) ABACUSerror("Please only populate a virgin Scan_State_List.");
//std::cout << "In Populate_List: " << State[0] << std::endl;
Vect<long long int> bases_id = State[0].chain.Possible_Bases (State[0].base.Mdown); // returns a vector of possible bases
//std::cout << "Mdown = " << State[0].base.Mdown << "\tPossible bases size: " << bases_id.size() << "\tPossible bases: " << bases_id << std::endl;
for (int ib = 0; ib < bases_id.size(); ++ib) {
ODSLF_Base checkbase (State[0].chain, bases_id[ib]);
Vect<long long int> types_id = checkbase.Possible_Types (); // returns a vector of possible types
//std::cout << "For base_id " << bases_id[ib] << "\t found types " << types_id << std::endl;
for (int it = 0; it < types_id.size(); ++it) {
if (bases_id[ib] < 1000000) { // FUDGE: consider only one-strings
//std::cout << "Populate list: constructing state: " << bases_id[ib] << "\t" << types_id[it] << std::endl;
State[ndef] = ODSLF_XXZ_Bethe_State (State[0].chain, bases_id[ib], types_id[it]);
//std::cout << "Populate list: before setting id: " << std::endl << State[ndef] << std::endl;
State[ndef].Set_to_id(0LL);
//std::cout << "Populate list: after setting id: " << std::endl << State[ndef] << std::endl;
info[ndef].Nfull = State[ndef].maxid + 1LL;
ndef++;
if (ndef >= MAX_STATE_LIST_SIZE) ABACUSerror("Increase number of elements in ScanStateList.");
}
}
}
}
*/
template<class Tstate>
inline void Scan_State_List<Tstate>::Include_Info (Scan_Info& info_to_add, std::string base_label_ref)
{
int n = 0;
while (n < ndef && base_label_ref.compare(base_label[n]) != 0) n++;
if (n == ndef) {
std::cout << "ndef = " << ndef << std::endl;
for (int i = 0; i < ndef; ++i) std::cout << base_label[i] << "\t";
std::cout << std::endl;
std::cout << "base_label_ref " << base_label_ref << std::endl;
ABACUSerror("Did not find base_label_ref in Scan_State_List::Include_Info.");
}
info[n] += info_to_add;
return;
}
template<class Tstate>
inline void Scan_State_List<Tstate>::Raise_Scanning_Flags (DP threshold)
{
flag_for_scan = true;
}
template<class Tstate>
inline void Scan_State_List<Tstate>::Order_in_SRC ()
{
if (ndef > 0) {
Vect_INT index(ndef);
for (int i = 0; i < ndef; ++i) index[i] = i;
Vect<DP> sr (ndef);
for (int i = 0; i < ndef; ++i) sr[i] = info[i].sumrule_obtained;
sr.QuickSort(index, 0, ndef - 1);
Vect<Tstate> State_ordered(ndef);
Vect<std::string> base_label_ordered(ndef);
Vect<Scan_Info> info_ordered(ndef);
Vect<bool> flag_for_scan_ordered(ndef);
// Put data in proper order
for (int i = 0; i < ndef; ++i) {
State_ordered[i] = State[index[ndef - 1 - i] ];
base_label_ordered[i] = base_label[index[ndef - 1 - i] ];
info_ordered[i] = info[index[ndef - 1 - i] ];
flag_for_scan_ordered[i] = flag_for_scan[index[ndef - 1 - i] ];
}
// Put back in *this object:
for (int i = 0; i < ndef; ++i) {
State[i] = State_ordered[i];
base_label[i] = base_label_ordered[i];
info[i] = info_ordered[i];
flag_for_scan[i] = flag_for_scan_ordered[i];
} // The rest are all simply 0.
}
}
template<class Tstate>
inline void Scan_State_List<Tstate>::Save_Info (const char* sumfile_Cstr)
{
std::ofstream outfile;
outfile.open(sumfile_Cstr);
if (outfile.fail()) ABACUSerror("Could not open outfile... ");
outfile.setf(std::ios::fixed);
outfile.precision(16);
outfile << std::setw(20) << "base" << std::setw(25) << "sumrule_obtained" << std::setw(25) << "Nfull" << std::setw(10) << "Ninadm" << std::setw(10) << "Ndata" << std::setw(10) << "conv" << std::setw(10) << "conv0" << std::setw(10) << "TT.";
for (int i = 0; i < ndef; ++i)
if (info[i].Nfull > 0.0) {
int TT_hr = int(info[i].TT/3600);
int TT_min = int((info[i].TT - 3600.0*TT_hr)/60);
outfile << std::endl << std::setw(20) << base_label[i] << std::setw(25) << std::fixed << std::setprecision(20) << info[i].sumrule_obtained;
if (info[i].Nfull < 1.0e+10) outfile << std::setw(25) << std::fixed << std::setprecision(0) << info[i].Nfull;
else outfile << std::setw(25) << std::scientific << std::setprecision(16) << info[i].Nfull;
outfile << std::setw(10) << info[i].Ninadm << std::setw(10) << info[i].Ndata << std::setw(10) << info[i].Ndata_conv << std::setw(10) << info[i].Ndata_conv0 << std::setw(10) << TT_hr << " h " << TT_min << " m " << std::fixed << std::showpoint << std::setprecision(3) << info[i].TT - 3600.0*TT_hr - 60.0*TT_min << " s";
}
outfile.close();
}
template<class Tstate>
inline void Scan_State_List<Tstate>::Load_Info (const char* sumfile_Cstr)
{
std::ifstream infile;
infile.open(sumfile_Cstr);
if(infile.fail()) {
std::cout << std::endl << sumfile_Cstr << std::endl;
ABACUSerror("Could not open input file in Scan_State_List::Load_Info.");
}
// Load first line, containing informative text:
char junk[256];
infile.getline(junk, 256);
// Now load the previous info's:
std::string base_label_ref;
DP sr_ref;
DP Nfull_ref;
long long int Ninadm_ref, Ndata_ref, conv_ref, conv0_ref;
DP TT_ref;
int TT_hr, TT_min;
DP TT_sec;
char a;
while (infile.peek() != EOF) {
infile >> base_label_ref >> sr_ref >> Nfull_ref >> Ninadm_ref >> Ndata_ref >> conv_ref >> conv0_ref >> TT_hr >> a >> TT_min >> a >> TT_sec >> a;
TT_ref = 3600.0 * TT_hr + 60.0* TT_min + TT_sec;
Scan_Info info_ref (sr_ref, Nfull_ref, Ninadm_ref, Ndata_ref, conv_ref, conv0_ref, TT_ref);
(*this).Include_Info (info_ref, base_label_ref);
}
infile.close();
return;
}
} // namespace ABACUS
#endif
@@ -2,24 +2,22 @@
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC_Spec_Fns.h
File: ABACUS_Spec_Fns.h
Purpose: Defines special math functions.
***********************************************************/
#ifndef _JSC_SPEC_FNS_H_
#define _JSC_SPEC_FNS_H_
#ifndef ABACUS_SPEC_FNS_H
#define ABACUS_SPEC_FNS_H
#include "JSC.h"
#include "ABACUS.h"
using namespace std;
namespace JSC {
namespace ABACUS {
inline DP Cosine_Integral (DP x)
{
@@ -28,8 +26,8 @@ namespace JSC {
// Refer to GR[6] 8.23
if (x <= 0.0) {
cout << "Cosine_Integral called with real argument " << x << " <= 0, which is ill-defined because of the branch cut." << endl;
JSCerror("");
std::cout << "Cosine_Integral called with real argument " << x << " <= 0, which is ill-defined because of the branch cut." << std::endl;
ABACUSerror("");
}
else if (x < 15.0) { // Use power series expansion
@@ -45,7 +43,7 @@ namespace JSC {
DP series = minonetothen * exp(logxtothetwon - log(2.0 * n) - logtwonfact);
DP term_n;
do {
do {
n += 1;
minonetothen *= -1.0;
logxtothetwon += twologx;
@@ -55,34 +53,6 @@ namespace JSC {
} while (fabs(term_n) > 1.0e-16);
/*
// For improved convergence we pair terms up, DOESN'T WORK WELL
// Ci (x) = gamma + \ln x - \sum{n = 1, 3, 5, ...} \frac{x^{2n}}{2n (2n)!} ( 1 - \frac{n}{n+1} \frac{x^2}{(2n+1)(2n+2)} )
int n = 1;
DP logxtothetwon = 2.0 * log(x);
DP logtwon = log(2.0);
DP logtwonfact = log(2.0);
DP xsq = x*x;
DP series = exp(logxtothetwon - logtwon - logtwonfact) * (1 - xsq/((2.0 * n + 1.0) * (2.0 * n + 2.0) * (1.0 + 1.0/n)));
DP term_n;
DP twologx = 2.0 * log(x);
do {
n += 2;
logxtothetwon += twologx;
logtwonfact += log((2.0 * n - 1.0) * 2.0 * n);
term_n = exp(logxtothetwon - log(2.0 * n) - logtwonfact) * (1 - xsq/((2.0 * n + 1.0) * (2.0 * n + 2.0) * (1.0 + 1.0/n)));;
series += term_n;
} while (fabs(term_n) > 1.0e-16);
*/
return(Euler_Mascheroni + log(x) + series);
}
@@ -102,7 +72,7 @@ namespace JSC {
DP series1 = minonetothen * exp(logtwonfact - logxtothetwon);
DP series2 = minonetothen * exp(logtwonplus1fact - logxtothetwonplus1);
do {
do {
n += 1;
minonetothen *= -1.0;
logxtothetwon += twologx;
@@ -133,11 +103,11 @@ namespace JSC {
// in which q is the nome. (GR 8.180.1)
// We always evaluate to numerical accuracy.
if (q >= 1.0) JSCerror("Jacobi_Theta_1_q function called with q > 1.");
if (q >= 1.0) ABACUSerror("Jacobi_Theta_1_q function called with q > 1.");
DP answer = 0.0;
DP contrib = 0.0;
DP contrib = 0.0;
DP qtonminhalfsq = pow(q, 0.25); // this will be q^{(n-1/2)^2}
DP qtotwon = pow(q, 2.0); // this will be q^{2n}
DP qsq = q*q;
@@ -149,26 +119,24 @@ namespace JSC {
qtonminhalfsq *= qtotwon;
qtotwon *= qsq;
n++;
//cout << "\t\tn = " << n << "\tanswer = " << answer << "\tcontrib = " << contrib << "\tqtonminhalfsq = " << qtonminhalfsq << "\tqtotwon = " << qtotwon << endl;
} while (fabs(contrib/answer) > MACHINE_EPS);
//cout << "\t\tJacobi_Theta_1: used " << n << " iterations." << "\tanswer = " << answer << "\tcontrib = " << contrib << "\tqtonminhalfsq = " << qtonminhalfsq << "\tqtotwon = " << qtotwon << endl;
return(answer);
}
inline complex<DP> ln_Jacobi_Theta_1_q (complex<DP> u, complex<DP> q) {
inline std::complex<DP> ln_Jacobi_Theta_1_q (std::complex<DP> u, std::complex<DP> q) {
// This uses the product representation
// \theta_1 (x) = 2 q^{1/4} \sin{u} \prod_{n=1}^\infty (1 - 2 q^{2n} \cos 2u + q^{4n}) (1 - q^{2n})
// (GR 8.181.2)
complex<DP> contrib = 0.0;
complex<DP> qtotwon = q*q; // this will be q^{2n}
complex<DP> qsq = q*q;
complex<DP> twocos2u = 2.0 * cos(2.0*u);
std::complex<DP> contrib = 0.0;
std::complex<DP> qtotwon = q*q; // this will be q^{2n}
std::complex<DP> qsq = q*q;
std::complex<DP> twocos2u = 2.0 * cos(2.0*u);
int n = 1;
complex<DP> answer = log(2.0 * sin(u)) + 0.25 * log(q);
std::complex<DP> answer = log(2.0 * sin(u)) + 0.25 * log(q);
do {
contrib = log((1.0 - twocos2u * qtotwon + qtotwon * qtotwon) * (1.0 - qtotwon));
answer += contrib;
@@ -184,7 +152,7 @@ namespace JSC {
inline DP ln_Gamma_for_Barnes_G_RE (Vect_DP args)
{
return(real(ln_Gamma(complex<double>(args[0]))));
return(real(ln_Gamma(std::complex<double>(args[0]))));
}
inline DP ln_Barnes_G_RE (DP z)
@@ -199,9 +167,9 @@ namespace JSC {
int max_nr_pts = 10000;
Integral_result integ_ln_Gamma = Integrate_optimal (ln_Gamma_for_Barnes_G_RE, args, 0, 0.0, z - 1.0, req_rel_prec, req_abs_prec, max_nr_pts);
return(0.5 * (z - 1.0) * (2.0 - z + logtwoPI) + (z - 1.0) * real(ln_Gamma(complex<double>(z - 1.0))) - integ_ln_Gamma.integ_est);
return(0.5 * (z - 1.0) * (2.0 - z + logtwoPI) + (z - 1.0) * real(ln_Gamma(std::complex<double>(z - 1.0))) - integ_ln_Gamma.integ_est);
}
} // namespace JSC
} // namespace ABACUS
#endif // _JS_SPEC_FNS_H_
#endif
@@ -2,23 +2,22 @@
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC_State_Ensemble.h
File: ABACUS_State_Ensemble.h
Purpose: Define state ensembles.
***********************************************************/
#ifndef _ENS_
#define _ENS_
#ifndef ABACUS_STATE_ENSEMBLE_H
#define ABACUS_STATE_ENSEMBLE_H
#include "JSC.h"
#include "ABACUS.h"
namespace JSC {
namespace ABACUS {
struct LiebLin_Diagonal_State_Ensemble {
@@ -29,8 +28,6 @@ namespace JSC {
LiebLin_Diagonal_State_Ensemble ();
LiebLin_Diagonal_State_Ensemble (const LiebLin_Bethe_State& RefState, int nstates_req);
//LiebLin_Diagonal_State_Ensemble (const LiebLin_Bethe_State& RefState, int nstates_req, const Vect<DP>& weight_ref);
//LiebLin_Diagonal_State_Ensemble (DP c_int, DP L, int N, const Root_Density& rho, int nstates_req);
LiebLin_Diagonal_State_Ensemble (DP c_int, DP L, int N, const Root_Density& rho);
LiebLin_Diagonal_State_Ensemble& operator= (const LiebLin_Diagonal_State_Ensemble& rhs);
@@ -38,10 +35,9 @@ namespace JSC {
void Save (const char* ensfile_Cstr);
};
//LiebLin_Diagonal_State_Ensemble LiebLin_Thermal_Saddle_Point_Ensemble (DP c_int, DP L, int N, DP kBT, int nstates_req);
LiebLin_Diagonal_State_Ensemble LiebLin_Thermal_Saddle_Point_Ensemble (DP c_int, DP L, int N, DP kBT);
} // namespace JSC
} // namespace ABACUS
#endif
+23 -25
View File
@@ -2,26 +2,25 @@
This software is part of J.-S. Caux's ABACUS. library.
Copyright (c).
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC_TBA.h
File: ABACUS_TBA.h
Purpose: Thermodynamic Bethe Ansatz general functions
***********************************************************/
#ifndef _TBA_
#define _TBA_
#ifndef ABACUS_TBA_H
#define ABACUS_TBA_H
#include "JSC.h"
#include "ABACUS.h"
namespace JSC {
namespace ABACUS {
struct Root_Density {
int Npts; // how many points are used to describe each function
DP lambdamax; // what the largest rapidity is
Vect_DP lambda; // rapidity vector
@@ -31,42 +30,42 @@ namespace JSC {
DP diff; // relative differences with previous iteration
bool value_infty_set; // boolean, true if asymptotic value set
DP value_infty; // asymptotic value, computed analytically
Root_Density ();
Root_Density (int Npts_ref, DP lambdamax_ref);
Root_Density& operator= (const Root_Density& RefDensity);
void Save (const char* outfile_Cstr);
DP Return_Value (DP lambda_ref); // evaluates the function for any argument using linear interpolation
void Set_Asymptotics (DP value_infty_ref); // sets value for lambda >= lambdamax
Root_Density Compress_and_Match_Densities (DP comp_factor); // returns a Root_Density with fewer points
};
struct Root_Density_Set {
int ntypes;
Vect<Root_Density> epsilon;
int Npts_total; // sum of all Npts of epsilon's
DP diff; // sum of diff's of the epsilon's
Root_Density_Set ();
Root_Density_Set (int ntypes_ref, int Npts_ref, DP lambdamax_ref);
Root_Density_Set (int ntypes_ref, Vect_INT Npts_ref, Vect_DP lambdamax_ref);
Root_Density_Set& operator= (const Root_Density_Set& RefSet);
void Insert_new_function (DP asymptotic_value);
void Extend_limits (Vect<bool> need_to_extend_limit);
void Insert_new_points (Vect<Vect<bool> > need_new_point_around);
DP Return_Value (int n_ref, DP lambda_ref); // returns a value, no matter what.
Root_Density_Set Return_Compressed_and_Matched_Set (DP comp_factor);
void Match_Densities (Root_Density_Set& RefSet);
void Save (const char* outfile_Cstr);
};
@@ -100,13 +99,13 @@ namespace JSC {
Root_Density LiebLin_rho_TBA (DP kBT, const Root_Density& epsilon, const Root_Density& depsilon_dmu);
Root_Density LiebLin_rhoh_TBA (DP kBT, const Root_Density& epsilon, const Root_Density& depsilon_dmu);
DP LiebLin_nbar_TBA (const Root_Density& rho);
DP LiebLin_ebar_TBA (const Root_Density& rho);
DP LiebLin_sbar_TBA (const Root_Density& rho, const Root_Density& rhoh);
DP LiebLin_ebar_TBA (const Root_Density& rho);
DP LiebLin_sbar_TBA (const Root_Density& rho, const Root_Density& rhoh);
LiebLin_TBA_Solution LiebLin_TBA_Solution_fixed_nbar (DP c_int, DP nbar_required, DP kBT, DP req_diff, int Max_Secs);
LiebLin_TBA_Solution LiebLin_TBA_Solution_fixed_nbar_ebar (DP c_int, DP nbar_required, DP ebar_required, DP req_diff, int Max_Secs);
LiebLin_Bethe_State Discretized_LiebLin_Bethe_State (DP c_int, DP L, int N, const Root_Density& rho);
// Functions defined in TBA_XXZ.cc
// Functions defined in TBA_XXZ.cc
DP XXZ_phi1_kernel (DP zeta, DP lambda);
DP XXZ_phi2_kernel (DP zeta, DP lambda);
DP XXZ_a1_kernel (DP sinzeta, DP coszeta, DP lambda);
@@ -121,7 +120,6 @@ namespace JSC {
Root_Density XXZ_Kbackflow_GS (DP Delta, DP B, DP lambdamax, DP lambda_p, DP lambda_h, int Npts, DP req_prec);
Root_Density XXZ_Fbackflow_GS (DP Delta, DP B, DP lambdamax, DP lambda_p, DP lambda_h, int Npts, DP req_prec);
Root_Density XXZ_Z_GS (DP Delta, DP B, DP lambdamax, int Npts, DP req_prec);
//void XXZ_Compare_Lattice_and_Continuum_Backflows_base_1010 (DP Delta, int N, int M, long long int id);
// Defined in TBA_2CBG.cc:
struct TBA_Data_2CBG {
@@ -141,7 +139,7 @@ namespace JSC {
void Scan_2CBG_TBAE (DP c_int, DP mu_min, DP mu_max, int Nmu, DP Omega_min, DP Omega_max, int NOmega,
DP kBT_min, DP kBT_max, int NkBT, int Max_Secs);
} // namespace JSC
} // namespace ABACUS
#endif
+438
View File
@@ -0,0 +1,438 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: ABACUS_util.h
Purpose: Defines basic math functions.
***********************************************************/
#ifndef ABACUS_UTIL_H
#define ABACUS_UTIL_H
#include "ABACUS.h"
typedef double DP;
// Global constants
const double PI = 3.141592653589793238462643;
const double sqrtPI = sqrt(PI);
const double twoPI = 2.0*PI;
const double logtwoPI = log(twoPI);
const double Euler_Mascheroni = 0.577215664901532860606;
const double Gamma_min_0p5 = -2.0 * sqrt(PI);
const std::complex<double> II(0.0,1.0); // Shorthand for i
const DP MACHINE_EPS = std::numeric_limits<DP>::epsilon();
const DP MACHINE_EPS_SQ = pow(MACHINE_EPS, 2.0);
// Now for some basic math utilities:
namespace ABACUS {
// File checks:
inline bool file_exists (const char* filename)
{
std::fstream file;
file.open(filename);
bool exists = !file.fail();
file.close();
return(exists);
}
// Error handler:
inline void ABACUSerror (const std::string error_text)
// my error handler
{
std::cerr << "Run-time error... " << std::endl;
std::cerr << error_text << std::endl;
std::cerr << "Exiting to system..." << std::endl;
exit(1);
}
struct Divide_by_zero {};
// Basics: min, max, fabs
template<class T>
inline const T max (const T& a, const T& b) { return a > b ? (a) : (b); }
template<class T>
inline const T min (const T& a, const T& b) { return a > b ? (b) : (a); }
template<class T>
inline const T fabs (const T& a) { return a >= 0 ? (a) : (-a); }
inline long long int pow_lli (const long long int& base, const int& exp)
{
long long int answer = base;
if (exp == 0) answer = 1LL;
else for (int i = 1; i < exp; ++i) answer *= base;
return(answer);
}
inline unsigned long long int pow_ulli (const unsigned long long int& base, const int& exp)
{
unsigned long long int answer = base;
if (exp == 0) answer = 1ULL;
for (int i = 1; i < exp; ++i) answer *= base;
return(answer);
}
inline int fact (const int& N)
{
int ans = 0;
if (N < 0) {
std::cerr << "Error: factorial of negative number. Exited." << std::endl;
exit(1);
}
else if ( N == 1 || N == 0) ans = 1;
else ans = N * fact(N-1);
return(ans);
}
inline DP ln_fact (const int& N)
{
DP ans = 0.0;
if (N < 0) {
std::cerr << "Error: factorial of negative number. Exited." << std::endl;
exit(1);
}
else if ( N == 1 || N == 0) ans = 0.0;
else ans = log(DP(N)) + ln_fact(N-1);
return(ans);
}
inline long long int fact_lli (const int& N)
{
long long int ans = 0;
if (N < 0) {
std::cerr << "Error: factorial of negative number. Exited." << std::endl;
exit(1);
}
else if ( N == 1 || N == 0) ans = 1;
else ans = fact_lli(N-1) * N;
return(ans);
}
inline long long int fact_ulli (const int& N)
{
unsigned long long int ans = 0;
if (N < 0) {
std::cerr << "Error: factorial of negative number. Exited." << std::endl;
exit(1);
}
else if ( N == 1 || N == 0) ans = 1;
else ans = fact_ulli(N-1) * N;
return(ans);
}
inline int choose (const int& N1, const int& N2)
{
// returns N1 choose N2
int ans = 0;
if (N1 < N2) {
std::cout << "Error: N1 smaller than N2 in choose. Exited." << std::endl;
exit(1);
}
else if (N1 == N2) ans = 1;
else if (N1 < 12) ans = fact(N1)/(fact(N2) * fact(N1 - N2));
else {
ans = 1;
int mult = N1;
while (mult > max(N2, N1 - N2)) ans *= mult--;
ans /= fact(min(N2, N1 - N2));
}
return(ans);
}
inline DP ln_choose (const int& N1, const int& N2)
{
// returns the log of N1 choose N2
DP ans = 0.0;
if (N1 < N2) {
std::cout << "Error: N1 smaller than N2 in choose. Exited." << std::endl;
exit(1);
}
else if (N1 == N2) ans = 0.0;
else ans = ln_fact(N1) - ln_fact(N2) - ln_fact(N1 - N2);
return(ans);
}
inline long long int choose_lli (const int& N1, const int& N2)
{
// returns N1 choose N2
long long int ans = 0;
if (N1 < N2) {
std::cout << "Error: N1 smaller than N2 in choose. Exited." << std::endl;
exit(1);
}
else if (N1 == N2) ans = 1;
else if (N1 < 12) ans = fact_lli(N1)/(fact_lli(N2) * fact_lli(N1 - N2));
else {
// Make sure that N2 is less than or equal to N1/2; if not, just switch...
int N2_min = min(N2, N1 - N2);
ans = 1;
for (int i = 0; i < N2_min; ++i) {
ans *= (N1 - i);
ans /= i + 1;
}
}
return(ans);
}
inline unsigned long long int choose_ulli (const int& N1, const int& N2)
{
// returns N1 choose N2
unsigned long long int ans = 0;
if (N1 < N2) {
std::cout << "Error: N1 smaller than N2 in choose. Exited." << std::endl;
exit(1);
}
else if (N1 == N2) ans = 1;
else if (N1 < 12) ans = fact_ulli(N1)/(fact_ulli(N2) * fact_ulli(N1 - N2));
else {
// Make sure that N2 is less than or equal to N1/2; if not, just switch...
int N2_min = min(N2, N1 - N2);
ans = 1;
for (int i = 0; i < N2_min; ++i) {
ans *= (N1 - i);
ans /= i + 1;
}
}
return(ans);
}
inline DP SIGN (const DP &a, const DP &b)
{
return b >= 0 ? (a >= 0 ? a : -a) : (a >= 0 ? -a : a);
}
inline DP sign_of (const DP& a)
{
return (a >= 0.0 ? 1.0 : -1.0);
}
inline int sgn_int (const int& a)
{
return (a >= 0) ? 1 : -1;
}
inline int sgn_DP (const DP& a)
{
return (a >= 0) ? 1 : -1;
}
template<class T>
inline void SWAP (T& a, T& b) {T dum = a; a = b; b = dum;}
inline int kronecker (int a, int b)
{
return a == b ? 1 : 0;
}
template<class T>
inline bool is_nan (const T& a)
{
return(!((a < T(0.0)) || (a >= T(0.0))));
}
inline std::complex<DP> atan_cx(const std::complex<DP>& x)
{
return(-0.5 * II * log((1.0 + II* x)/(1.0 - II* x)));
}
/**************** Gamma function *******************/
inline std::complex<double> ln_Gamma (std::complex<double> z)
{
// Implementation of Lanczos method with g = 9.
// Coefficients from Godfrey 2001.
if (real(z) < 0.5) return(log(PI/(sin(PI*z))) - ln_Gamma(1.0 - z));
else {
std::complex<double> series = 1.000000000000000174663
+ 5716.400188274341379136/z
- 14815.30426768413909044/(z + 1.0)
+ 14291.49277657478554025/(z + 2.0)
- 6348.160217641458813289/(z + 3.0)
+ 1301.608286058321874105/(z + 4.0)
- 108.1767053514369634679/(z + 5.0)
+ 2.605696505611755827729/(z + 6.0)
- 0.7423452510201416151527e-2 / (z + 7.0)
+ 0.5384136432509564062961e-7 / (z + 8.0)
- 0.4023533141268236372067e-8 / (z + 9.0);
return(0.5 * logtwoPI + (z - 0.5) * log(z + 8.5) - (z + 8.5) + log(series));
}
return(log(0.0)); // never called
}
inline std::complex<double> ln_Gamma_old (std::complex<double> z)
{
// Implementation of Lanczos method with g = 9.
// Coefficients from Godfrey 2001.
if (real(z) < 0.5) return(log(PI/(sin(PI*z))) - ln_Gamma(1.0 - z));
else {
int g = 9;
double p[11] = { 1.000000000000000174663,
5716.400188274341379136,
-14815.30426768413909044,
14291.49277657478554025,
-6348.160217641458813289,
1301.608286058321874105,
-108.1767053514369634679,
2.605696505611755827729,
-0.7423452510201416151527e-2,
0.5384136432509564062961e-7,
-0.4023533141268236372067e-8 };
std::complex<double> z_min_1 = z - 1.0;
std::complex<double> series = p[0];
for (int i = 1; i < g+2; ++i)
series += p[i]/(z_min_1 + std::complex<double>(i));
return(0.5 * logtwoPI + (z_min_1 + 0.5) * log(z_min_1 + std::complex<double>(g) + 0.5)
- (z_min_1 + std::complex<double>(g) + 0.5) + log(series));
}
return(log(0.0)); // never called
}
inline std::complex<double> ln_Gamma_2 (std::complex<double> z)
{
// Implementation of Lanczos method with g = 7.
if (real(z) < 0.5) return(log(PI/(sin(PI*z)) - ln_Gamma(1.0 - z)));
else {
int g = 7;
double p[9] = { 0.99999999999980993, 676.5203681218851, -1259.1392167224028,
771.32342877765313, -176.61502916214059, 12.507343278686905,
-0.13857109526572012, 9.9843695780195716e-6, 1.5056327351493116e-7};
std::complex<double> z_min_1 = z - 1.0;
std::complex<double> series = p[0];
for (int i = 1; i < g+2; ++i)
series += p[i]/(z_min_1 + std::complex<double>(i));
return(0.5 * logtwoPI + (z_min_1 + 0.5) * log(z_min_1 + std::complex<double>(g) + 0.5)
- (z_min_1 + std::complex<double>(g) + 0.5) + log(series));
}
return(log(0.0)); // never called
}
/********** Partition numbers **********/
inline long long int Partition_Function (int n)
{
// Returns the value of the partition function p(n), giving the number of partitions of n into integers.
if (n < 0) ABACUSerror("Calling Partition_Function for n < 0.");
else if (n == 0 || n == 1) return(1LL);
else if (n == 2) return(2LL);
else if (n == 3) return(3LL);
else { // do recursion using pentagonal numbers
long long int pn = 0LL;
int pentnrplus, pentnrmin; // pentagonal numbers
for (int i = 1; true; ++i) {
pentnrplus = (i * (3*i - 1))/2;
pentnrmin = (i * (3*i + 1))/2;
if (n - pentnrplus >= 0) pn += (i % 2 ? 1LL : -1LL) * Partition_Function (n - pentnrplus);
if (n - pentnrmin >= 0) pn += (i % 2 ? 1LL : -1LL) * Partition_Function (n - pentnrmin);
else break;
}
return(pn);
}
return(-1LL); // never called
}
/********** Sorting **********/
template <class T>
void QuickSort (T* V, int l, int r)
{
int i = l, j = r;
T pivot = V[l + (r-l)/2];
while (i <= j) {
while (V[i] < pivot) i++;
while (V[j] > pivot) j--;
if (i <= j) {
std::swap(V[i],V[j]);
i++;
j--;
}
};
if (l < j) QuickSort(V, l, j);
if (i < r) QuickSort(V, i, r);
}
template <class T>
void QuickSort (T* V, int* index, int l, int r)
{
int i = l, j = r;
T pivot = V[l + (r-l)/2];
while (i <= j) {
while (V[i] < pivot) i++;
while (V[j] > pivot) j--;
if (i <= j) {
std::swap(V[i],V[j]);
std::swap(index[i],index[j]);
i++;
j--;
}
};
if (l < j) QuickSort(V, index, l, j);
if (i < r) QuickSort(V, index, i, r);
}
} // namespace ABACUS
#endif
+60 -175
View File
@@ -2,20 +2,20 @@
This software is part of J.-S. Caux's ABACUS++ library.
Copyright (c)
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC_Vect.h
File: ABACUS_Vect.h
Purpose: Declares vector class.
***********************************************************/
#ifndef _JSC_VECT_
#define _JSC_VECT_
#ifndef ABACUS_VECT_H
#define ABACUS_VECT_H
namespace JSC {
namespace ABACUS {
template <class T>
class Vect {
@@ -32,7 +32,7 @@ namespace JSC {
Vect& operator= (const T& a); // assign a to all elements
inline T& operator[] (const int i);
inline const T& operator[] (const int i) const;
Vect& operator+= (const Vect& rhs);
Vect& operator+= (const Vect& rhs);
Vect& operator-= (const Vect& rhs);
bool operator== (const Vect& rhs); // checks equality of size and of all elements
bool operator!= (const Vect& rhs); // checks inequality
@@ -52,31 +52,31 @@ namespace JSC {
void QuickSort (Vect<int>& index);
~Vect();
};
template <class T>
Vect<T>::Vect() : dim(0), V(0) {}
template <class T>
Vect<T>::Vect (int N) : dim(N), V(new T[N]) {}
template <class T>
Vect<T>::Vect (const T& a, int N) : dim(N), V(new T[N])
{
for (int i = 0; i < N; ++i) V[i] = a;
}
{
for (int i = 0; i < N; ++i) V[i] = a;
}
template <class T>
Vect<T>::Vect (const T* a, int N) : dim(N), V(new T[N])
{
for (int i = 0; i < N; ++i) V[i] = *a++;
}
{
for (int i = 0; i < N; ++i) V[i] = *a++;
}
template <class T>
Vect<T>::Vect (const Vect<T>& rhs) : dim(rhs.dim), V(new T[dim])
{
for (int i = 0; i < dim; ++i) V[i] = rhs[i];
}
{
for (int i = 0; i < dim; ++i) V[i] = rhs[i];
}
template <class T>
Vect<T>& Vect<T>::operator= (const Vect<T>& rhs)
{
@@ -90,7 +90,7 @@ namespace JSC {
}
return *this;
}
template <class T>
Vect<T>& Vect<T>::operator= (const T& a)
{
@@ -100,15 +100,15 @@ namespace JSC {
template <class T>
inline T& Vect<T>::operator[] (const int i)
{
return V[i];
}
{
return V[i];
}
template <class T>
inline const T& Vect<T>::operator[] (const int i) const
{
return V[i];
}
{
return V[i];
}
template <class T>
Vect<T>& Vect<T>::operator+= (const Vect<T>& rhs)
@@ -116,7 +116,7 @@ namespace JSC {
for (int i = 0; i < dim; ++i) V[i] += rhs[i];
return *this;
}
template <class T>
Vect<T>& Vect<T>::operator-= (const Vect<T>& rhs)
{
@@ -138,7 +138,7 @@ namespace JSC {
bool Vect<T>::operator!= (const Vect<T>& rhs)
{
return(!((*this) == rhs));
}
}
template <class T>
bool Vect<T>::Append (const Vect<T>& rhs) // appends rhs to the vector
@@ -180,7 +180,7 @@ namespace JSC {
int resized_dim = dim + nr_to_add;
T* resized_vect = new T[resized_dim];
for (int i = 0; i < dim; ++i) resized_vect[i] = V[i];
for (int i = 0; i < dim; ++i) resized_vect[i] = V[i];
for (int i = dim; i < resized_dim; ++i) resized_vect[i] = T(0);
dim = resized_dim;
@@ -199,7 +199,7 @@ namespace JSC {
int resized_dim = dim + nr_to_add;
T* resized_vect = new T[resized_dim];
for (int i = 0; i < dim; ++i) resized_vect[i] = V[i];
for (int i = 0; i < dim; ++i) resized_vect[i] = V[i];
for (int i = dim; i < resized_dim; ++i) resized_vect[i] = setval;
dim = resized_dim;
@@ -215,12 +215,12 @@ namespace JSC {
template <class T>
inline int Vect<T>::size() const
{
return dim;
}
{
return dim;
}
template <class T>
inline double Vect<T>::norm () const
inline double Vect<T>::norm () const
{
double normsq = 0.0;
for (int i = 0; i < dim; ++i) normsq += abs(V[i]) * abs(V[i]);
@@ -228,7 +228,7 @@ namespace JSC {
}
template <>
inline double Vect<double>::norm () const
inline double Vect<double>::norm () const
{
double normsq = 0.0;
for (int i = 0; i < dim; ++i) normsq += V[i] * V[i];
@@ -236,7 +236,7 @@ namespace JSC {
}
template <>
inline double Vect<complex<double> >::norm () const
inline double Vect<std::complex<double> >::norm () const
{
double normsq = 0.0;
for (int i = 0; i < dim; ++i) normsq += std::norm(V[i]);
@@ -262,7 +262,7 @@ namespace JSC {
template <class T>
inline T Vect<T>::sum() const
{
T total = T(0);
T total = T(0);
for (int i = 0; i < dim; ++i) total += V[i];
return total;
}
@@ -275,69 +275,13 @@ namespace JSC {
return(index < dim);
}
/*
template <class T>
void Vect<T>::QuickSort (int l, int r)
{
//cout << "QuickSort called for l = " << l << "\t r = " << r << endl;
//cout << (*this) << endl;
//for (int ih = l; ih <= r; ++ih) cout << setprecision(16) << "ih = " << ih << "\tV[ih] = " << V[ih] << endl;
static T m;
static int j;
int i;
if (r > l) {
m = V[r]; i = l-1; j = r;
for (;;) {
while (V[++i] < m);
while (V[--j] > m);
if (i >= j) break;
std::swap(V[i], V[j]);
}
std::swap(V[i], V[r]);
(*this).QuickSort(l, i-1);
(*this).QuickSort(i+1, r);
}
}
*/
/*
template <class T>
void Vect<T>::QuickSort (int l, int r)
{
// My own version of QuickSort: add sentinels on left and right
if (r > l) {
int s = l + (r-l)/2; // central element index
// Rearrange so that V[l] <= V[s] <= V[r] (sentinels on left and right)
if (V[l] > V[r]) std::swap(V[l],V[r]);
if (V[s] > V[r]) std::swap(V[s],V[r]);
if (V[l] > V[s]) std::swap(V[l],V[s]);
m = V[s]; i = l-1; j = r;
//m = V[r]; i = l-1; j = r;
for (;;) {
while (V[i] < m) i++;
while (V[j] > m) j--;
if (i >= j) break;
std::swap(V[i], V[j]); // restart from indices i and j just used, in case one is pivot
}
//std::swap(V[i], V[r]);
(*this).QuickSort(l, i-1);
(*this).QuickSort(i+1, r);
}
}
*/
template <class T>
void Vect<T>::QuickSort (int l, int r)
{
int i = l, j = r;
T pivot = V[l + (r-l)/2];
while (i <= j) {
while (V[i] < pivot) i++;
while (V[j] > pivot) j--;
@@ -347,7 +291,7 @@ namespace JSC {
j--;
}
};
if (l < j) (*this).QuickSort(l, j);
if (i < r) (*this).QuickSort(i, r);
}
@@ -358,71 +302,12 @@ namespace JSC {
if ((*this).size() > 1) (*this).QuickSort (0, (*this).size() - 1);
}
/*
template <class T>
void Vect<T>::QuickSort (Vect<int>& index, int l, int r)
{
if (index.size() != (*this).size()) {
cout << (*this).size() << "\t" << index.size() << endl;
JSCerror("Wrong dim for index in Vect QuickSort.");
}
static T m;
static int j;
int i;
if (r > l) {
m = V[r]; i = l-1; j = r;
for (;;) {
while (V[++i] < m);
while (V[--j] > m);
if (i >= j) break;
std::swap(V[i], V[j]);
std::swap(index[i], index[j]);
}
std::swap(V[i], V[r]);
std::swap(index[i], index[r]);
(*this).QuickSort(index, l, i-1);
(*this).QuickSort(index, i+1, r);
}
}
*/
/*
template <class T>
void Vect<T>::QuickSort (Vect<int>& index, int l, int r)
{
// My own version of QuickSort:
if (r > l) {
int s = l + (r-l)/2; // central element index
// Rearrange so that V[l] <= V[s] <= V[r] (sentinels on left and right)
if (V[l] > V[r]) std::swap(V[l],V[r]);
if (V[s] > V[r]) std::swap(V[s],V[r]);
if (V[l] > V[s]) std::swap(V[l],V[s]);
m = V[s]; i = l-1; j = r+1;
for (;;) {
while (V[++i] < m);
while (V[--j] > m);
if (i >= j) break;
std::swap(index[i], index[j]);
std::swap(V[i--], V[j++]); // restart from indices i and j just used, in case one is pivot
}
(*this).QuickSort(index, l, i-1);
(*this).QuickSort(index, i+1, r);
}
}
*/
template <class T>
void Vect<T>::QuickSort (Vect<int>& index, int l, int r)
{
int i = l, j = r;
T pivot = V[l + (r-l)/2];
while (i <= j) {
while (V[i] < pivot) i++;
while (V[j] > pivot) j--;
@@ -433,7 +318,7 @@ namespace JSC {
j--;
}
};
if (l < j) (*this).QuickSort(index, l, j);
if (i < r) (*this).QuickSort(index, i, r);
}
@@ -441,32 +326,32 @@ namespace JSC {
template <class T>
void Vect<T>::QuickSort (Vect<int>& index)
{
if (index.size() != (*this).size()) JSCerror("Wrong dim for index in Vect QuickSort.");
if (index.size() != (*this).size()) ABACUSerror("Wrong dim for index in Vect QuickSort.");
(*this).QuickSort (index, 0, (*this).size() - 1);
}
template <class T>
inline std::ostream& operator<< (std::ostream& s, const Vect<T>& vector)
{
for (int i = 0; i < vector.size() - 1; ++i) s << vector[i] << " ";
if (vector.size() >= 1) s << vector[vector.size() - 1];
inline std::ostream& operator<< (std::ostream& s, const Vect<T>& vector)
{
for (int i = 0; i < vector.size() - 1; ++i) s << vector[i] << " ";
if (vector.size() >= 1) s << vector[vector.size() - 1];
return (s);
}
return (s);
}
template <class T>
Vect<T>::~Vect<T>()
{
if (V != 0) delete[] V;
}
{
if (V != 0) delete[] V;
}
// TYPEDEFS
typedef JSC::Vect<int> Vect_INT;
typedef JSC::Vect<double> Vect_DP;
typedef JSC::Vect<complex<double> > Vect_CX;
// TYPEDEFS
typedef ABACUS::Vect<int> Vect_INT;
typedef ABACUS::Vect<double> Vect_DP;
typedef ABACUS::Vect<std::complex<double> > Vect_CX;
} // namespace JSC
} // namespace ABACUS
#endif
@@ -2,56 +2,58 @@
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC_XXX_h0.h
Purpose: Declares classes for XXX in zero field: Uq(sl(2)) stuff.
File: ABACUS_XXX_VOA.h
Purpose: Declares classes for XXX in zero field: Vertex Operator Approach
***********************************************************/
#ifndef _XXX_h0_
#define _XXX_h0_
#ifndef ABACUS_XXX_VOA_H
#define ABACUS_XXX_VOA_H
#include "JSC.h"
#include "ABACUS.h"
const DP default_req_prec = 1.0e-14;
const int default_max_rec = 10;
namespace JSC {
namespace ABACUS {
inline DP Integrand_11 (Vect_DP args)
{
// args[0] corresponds to t, args[1] to rho
return((exp(args[0]) * sinh(args[0]) * cos(4.0 * args[0] * args[1])/(2.0 * pow(cosh(args[0]), 2.0)) + 2.0 * pow(sin(2.0 * args[0] * args[1]), 2.0))/args[0]);
}
{
// args[0] corresponds to t, args[1] to rho
return((exp(args[0]) * sinh(args[0]) * cos(4.0 * args[0] * args[1])
/(2.0 * pow(cosh(args[0]), 2.0)) + 2.0 * pow(sin(2.0 * args[0] * args[1]), 2.0))/args[0]);
}
inline DP Integrand_12 (Vect_DP args)
{
DP expm2t = exp(-2.0*args[0]);
return(cos(4.0 * args[0] * args[1]) * expm2t * (3.0 + expm2t)/ (args[0] * (1.0 + expm2t) * (1.0 + expm2t)));
}
{
DP expm2t = exp(-2.0*args[0]);
return(cos(4.0 * args[0] * args[1]) * expm2t * (3.0 + expm2t)/ (args[0] * (1.0 + expm2t) * (1.0 + expm2t)));
}
inline DP Integrand_2 (Vect_DP args)
{
DP answer = 0.0;
if (args[0] < 1.0) answer = exp(args[0]) * pow(sin(2.0 * args[0] * args[1]), 2.0)/(args[0] * sinh(args[0]) * pow(cosh(args[0]), 2.0));
else if (args[0] >= 1.0) {
DP expm2t = exp(-2.0 * args[0]);
answer = 8.0 * expm2t * pow(sin(2.0 * args[0] * args[1]), 2.0)/(args[0] * (1.0 - expm2t) * (1.0 + expm2t) * (1.0 + expm2t));
}
return(answer);
{
DP answer = 0.0;
if (args[0] < 1.0) answer = exp(args[0]) * pow(sin(2.0 * args[0] * args[1]), 2.0)
/(args[0] * sinh(args[0]) * pow(cosh(args[0]), 2.0));
else if (args[0] >= 1.0) {
DP expm2t = exp(-2.0 * args[0]);
answer = 8.0 * expm2t * pow(sin(2.0 * args[0] * args[1]), 2.0)
/(args[0] * (1.0 - expm2t) * (1.0 + expm2t) * (1.0 + expm2t));
}
return(answer);
}
inline DP Integrand_A (Vect_DP args)
{
// This kernel is for -ln | A_-(i\pi/2) | function
return(exp(args[0]) * pow(sinh(args[0]/2.0), 2.0)/(args[0] * sinh(2.0*args[0]) * cosh(args[0])));
}
{
// This kernel is for -ln | A_-(i\pi/2) | function
return(exp(args[0]) * pow(sinh(args[0]/2.0), 2.0)/(args[0] * sinh(2.0*args[0]) * cosh(args[0])));
}
DP I_integral (DP rho, DP req_prec);
@@ -73,32 +75,32 @@ namespace JSC {
DP SF_2p_check_fixed_k_sumrule_opt (DP k, DP req_prec, int Npts, I_table Itable);
/********************** FOUR SPINONS **********************/
/********************** FOUR SPINONS **********************/
DP Sum_norm_gl (Vect_DP rho, DP req_prec);
DP Compute_C4 (DP req_prec);
DP SF_contrib (Vect_DP p, DP req_prec, I_table Itable);
DP J_fn (Vect_DP p, DP req_prec, I_table Itable);
inline DP Jacobian_p3p4_KW (DP k, DP w, DP K, DP W)
{
return(1.0/sqrt(pow(twoPI * sin(0.5 * (k - K)), 2.0) - (w-W)*(w-W)));
}
{
return(1.0/sqrt(pow(twoPI * sin(0.5 * (k - K)), 2.0) - (w-W)*(w-W)));
}
bool Set_p_given_kwKW (DP k, DP w, DP K, DP W, Vect_DP& p);
inline DP wmin_4p (DP k)
{
return(PI * fabs(sin(k)));
}
}
inline DP wmax_4p (DP k)
{
return(2.0 * PI * sqrt(2.0 * (1.0 + fabs(cos(0.5*k)))));
}
inline DP Wmin (DP k, DP w, DP K)
{
return(JSC::max(1.0e-15, JSC::max(fabs(PI * sin(K)), w - twoPI * sin(0.5 * (fabs(k-K))))));
return(ABACUS::max(1.0e-15, ABACUS::max(fabs(PI * sin(K)), w - twoPI * sin(0.5 * (fabs(k-K))))));
}
inline DP Wmax (DP k, DP w, DP K)
{
return(JSC::min(twoPI * sin(0.5 * K), w - fabs(PI * sin(k - K))));
return(ABACUS::min(twoPI * sin(0.5 * K), w - fabs(PI * sin(k - K))));
}
DP G_fn (Vect_DP args_to_G, I_table Itable);
DP G1_fn (Vect_DP args_to_G, I_table Itable);
@@ -134,6 +136,6 @@ namespace JSC {
DP Direct_J_integral_bin (int Npts_p, int Npts_o, DP req_prec, I_table Itable);
void Smoothen_raw_SF_4p (int Npts_p, int Npts_o, DP req_prec, DP width);
} // namespace JSC
} // namespace ABACUS
#endif
+47
View File
@@ -0,0 +1,47 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: ABACUS_XXZ_VOA.h
Purpose: Declares classes for XXZ in zero field: Vertex Operator Approach
***********************************************************/
#ifndef ABACUS_XXZ_VOA_H
#define ABACUS_XXZ_VOA_H
#include "ABACUS.h"
namespace ABACUS {
DP I_xi_integral (DP xi, DP rho, DP req_prec, int max_nr_pts);
/********************* TWO SPINONS ********************/
DP Szz_XXZ_h0_2spinons (DP k, DP omega, Integral_table Itable);
DP Szz_XXZ_h0_2spinons (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_alt (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_omega (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_omega_alt (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_intomega (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_intomega_alt (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_check_sumrule (DP Delta, DP req_prec, int max_nr_pts, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_check_sumrule_alt (DP Delta, DP req_prec, int max_nr_pts, Integral_table Itable);
DP Fixed_k_sumrule_omega_Szz_XXZ_h0_N (DP Delta, DP k);
DP GSE_XXZ_h0 (DP Delta, DP req_prec, int max_nr_pts);
DP Fixed_k_sumrule_omega_Szz_XXZ_h0 (DP Delta, DP k, DP req_prec, int max_nr_pts);
DP Szz_XXZ_h0_2spinons_check_fixed_k_Szz_sumrule (DP Delta, DP k, DP req_prec, int max_nr_pts, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_check_fixed_k_Szz_sumrule_alt (DP Delta, DP k, DP req_prec, int max_nr_pts, Integral_table Itable);
//******************************** Functions to produce files similar to ABACUS **********************************
void Produce_Szz_XXZ_h0_2spinons_file (DP Delta, int N, int Nomega, DP omegamax, Integral_table Itable);
void Produce_Szz_XXZ_h0_2spinons_fixed_K_file (DP Delta, DP Kover2PI, int Nomega, Integral_table Itable);
} // namespace ABACUS
#endif
+12 -12
View File
@@ -2,22 +2,22 @@
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
Copyright (c) J.-S. Caux.
-----------------------------------------------------------
File: JSC_Young.h
File: ABACUS_Young.h
Purpose: Declares Young tableau class.
***********************************************************/
#ifndef _YOUNG_
#define _YOUNG_
#ifndef ABACUS_YOUNG_H
#define ABACUS_YOUNG_H
#include "JSC_Vect.h"
#include "ABACUS_Vect.h"
namespace JSC {
namespace ABACUS {
const int YOUNG_TABLEAU_ID_OPTION = 0;
const long long int TABLEAU_ID_UPPER_LIMIT = 10000000LL;
@@ -32,7 +32,7 @@ namespace JSC {
int* Row_L;
int* Col_L;
long long int id; // identification number
long long int maxid;
long long int maxid;
long long int* map;
bool map_computed;
long long int idnr_reached;
@@ -59,11 +59,11 @@ namespace JSC {
Young_Tableau& Set_Row_L (Vect<int>& Row_Lengths); // set row lengths
Young_Tableau& Set_Col_L_given_Row_L (); // sets the Col_L array self-consistently
Young_Tableau& Set_Row_L_given_Col_L (); // sets the Col_L array self-consistently
long long int Compute_Descendent_id (int option, Vect<int>& Desc_Row_L, int Nrows_Desc, int Ncols_Desc,
long long int Compute_Descendent_id (int option, Vect<int>& Desc_Row_L, int Nrows_Desc, int Ncols_Desc,
const Young_Tableau& RefTableau);
Young_Tableau& Compute_id(); // computes the id number of tableau
Young_Tableau& Compute_id(int option); // computes the id number of tableau according to rule option
Young_Tableau& Print(); // couts the tableau
Young_Tableau& Print(); // couts the tableau
bool Lower_Row (int i);
bool Raise_Row (int i);
@@ -104,15 +104,15 @@ namespace JSC {
Vect<long long int> map;
long long int idnr_reached;
int nboxes_reached;
public:
Tableau_Map (int Nrows, int Ncols);
void Distribute_id (int nboxes_to_dist, int level, Young_Tableau& RefTableau);
};
} // namespace JSC
} // namespace ABACUS
#endif
-777
View File
@@ -1,777 +0,0 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS++ library.
Copyright (c)
-----------------------------------------------------------
File: Heis.h
Purpose: Declares Heisenberg chain classes and functions.
***********************************************************/
#ifndef _HEIS_
#define _HEIS_
#include "JSC.h"
namespace JSC {
// First, some global constants...
const long long int ID_UPPER_LIMIT = 10000000LL; // max size of vectors we can define without seg fault
const int INTERVALS_SIZE = 100000; // size of Scan_Intervals arrays
const int NBASESMAX = 1000; // max number of bases kept
const DP ITER_REQ_PREC = 100.0 * MACHINE_EPS_SQ;
//const DP ITER_REQ_PREC = MACHINE_EPS_SQ;
// Cutoffs on particle numbers
//const int NPARTICLES_MAX = 24;
//const int NHOLES_MAX = NPARTICLES_MAX/2;
//const int MAX_RAPS_ABOVE_ZERO = 10; // max nr of rapidities above lowest type
//const int NPARTICLES_MAX = 2;
//const int NHOLES_MAX = 1;
//const int MAX_TYPES_IN_BASE = 4; // maximal number of particle types we allow in bases
const int MAXSTRINGS = 20; // maximal number of particle types we allow in bases
//const int MAXSTRINGS = 2; // maximal number of particle types we allow in bases
//const DP HEIS_deltaprec = 1.0e-6;//1.0e-4; // maximal string deviation allowed // DEPRECATED in ++T_9
const int NEXC_MAX_HEIS = 16; // maximal number of excitations (string binding/unbinding, particle-hole) considered
//***********************************************************************
class Heis_Chain {
public:
DP J;
DP Delta;
DP anis; // acos(Delta) if Delta < 1.0, 0 if Delta == 1.0, acosh(Delta) if Delta > 1.0
DP hz;
int Nsites;
int Nstrings; // how many possible strings. The following two arrays have Nstrings nonzero elements.
int* Str_L; // vector (length M) containing the allowed string lengths. Elements that are 0 have no meaning.
int* par; // vector (length M) containing the parities of the strings. Elements that are 0 have no meaning.
// Parities are all +1 except for gapless XXZ subcases
DP* si_n_anis_over_2; // for optimization: sin for XXZ, sinh for XXZ_gpd
DP* co_n_anis_over_2; // for optimization
DP* ta_n_anis_over_2; // for optimization
DP prec; // precision required for computations, always put to ITER_REQ_PREC
public:
Heis_Chain ();
Heis_Chain (DP JJ, DP DD, DP hh, int NN); // contructor: simply initializes
Heis_Chain (const Heis_Chain& RefChain); // copy constructor;
Heis_Chain& operator= (const Heis_Chain& RefChain);
bool operator== (const Heis_Chain& RefChain);
bool operator!= (const Heis_Chain& RefChain);
~Heis_Chain(); // destructor
public:
//void Scan_for_Possible_Bases (int Mdown, Vect<long long int>& possible_base_id, int& nfound, int nexc_max_used,
// int base_level_to_scan, Vect<int>& Nrapidities);
//Vect<long long int> Possible_Bases (int Mdown); // returns a vector of possible bases
/* Deactivated in ++G_8
void Scan_for_Possible_Bases (int Mdown, Vect<string>& possible_base_label, int& nfound, int nexc_max_used,
int base_level_to_scan, Vect<int>& Nrapidities);
Vect<string> Possible_Bases (int Mdown); // returns a vector of possible bases
*/
};
//****************************************************************************
// Objects in class Heis_Base are a checked vector containing the number of rapidities of allowable types for a given state
class Heis_Base {
public:
int Mdown; // total number of down spins
Vect<int> Nrap; // Nrap[i] contains the number of rapidities of type i, i = 0, Nstrings - 1.
int Nraptot; // total number of strings in this state
Vect<DP> Ix2_infty; // Ix2_infty[i] contains the max of BAE function for the (half-)integer I[i], i = 0, Nstrings - 1.
Vect<int> Ix2_min;
Vect<int> Ix2_max; // Ix2_max[i] contains the integer part of 2*I_infty, with correct parity for base.
//long long int id; // identification number
double dimH; // dimension of sub Hilbert space associated to this base; use double to avoid max int problems.
string baselabel; // base label
public:
Heis_Base ();
Heis_Base (const Heis_Base& RefBase); // copy constructor
Heis_Base (const Heis_Chain& RefChain, int M); // constructs configuration with all Mdown in one-string of +1 parity
Heis_Base (const Heis_Chain& RefChain, const Vect<int>& Nrapidities); // sets to Nrapidities vector, and checks consistency
//Heis_Base (const Heis_Chain& RefChain, long long int id_ref);
Heis_Base (const Heis_Chain& RefChain, string baselabel_ref);
inline int& operator[] (const int i);
inline const int& operator[] (const int i) const;
Heis_Base& operator= (const Heis_Base& RefBase);
bool operator== (const Heis_Base& RefBase);
bool operator!= (const Heis_Base& RefBase);
void Compute_Ix2_limits(const Heis_Chain& RefChain); // computes the Ix2_infty and Ix2_max
//void Scan_for_Possible_Types (Vect<long long int>& possible_type_id, int& nfound, int base_level, Vect<int>& Nexcitations);
//Vect<long long int> Possible_Types (); // returns a vector of possible types
};
inline int& Heis_Base::operator[] (const int i)
{
return Nrap[i];
}
inline const int& Heis_Base::operator[] (const int i) const
{
return Nrap[i];
}
//****************************************************************************
/*
// Objects in class Ix2_Config carry all the I's of a given state
class Ix2_Config {
//private:
public:
int Nstrings;
Vect<int> Nrap;
int Nraptot;
//int** Ix2;
Vect<Vect<int> > Ix2;
public:
Ix2_Config ();
Ix2_Config (const Heis_Chain& RefChain, int M); // constructor, puts I's to ground state
Ix2_Config (const Heis_Chain& RefChain, const Heis_Base& base); // constructor, putting I's to lowest-energy config
// consistent with Heis_Base configuration for chain RefChain
Ix2_Config& operator= (const Ix2_Config& RefConfig);
//inline int* operator[] (const int i);
inline Vect<int> operator[] (const int i);
//inline const int* operator[] (const int i) const;
inline const Vect<int> operator[] (const int i) const;
//~Ix2_Config(); // not needed, inherited from Vect
string Return_Label (const Ix2_Config& OriginIx2);
};
//inline int* Ix2_Config::operator[] (const int i)
inline Vect<int> Ix2_Config::operator[] (const int i)
{
return Ix2[i];
}
//inline const int* Ix2_Config::operator[] (const int i) const
inline const Vect<int> Ix2_Config::operator[] (const int i) const
{
return Ix2[i];
}
std::ostream& operator<< (std::ostream& s, const Ix2_Config& RefConfig);
*/
//****************************************************************************
// Objects in class Lambda carry all rapidities of a state
class Lambda {
private:
int Nstrings;
Vect<int> Nrap;
int Nraptot;
DP** lambda;
//Vect<Vect<DP> > lambda;
public:
Lambda ();
Lambda (const Heis_Chain& RefChain, int M); // constructor, puts all lambda's to zero
Lambda (const Heis_Chain& RefChain, const Heis_Base& base); // constructor, putting I's to lowest-energy config
// consistent with Heis_Base configuration for chain RefChain
Lambda& operator= (const Lambda& RefConfig);
inline DP* operator[] (const int i);
//inline Vect<DP> operator[] (const int i);
inline const DP* operator[] (const int i) const;
//inline const Vect<DP> operator[] (const int i) const;
~Lambda();
};
inline DP* Lambda::operator[] (const int i)
//inline Vect<DP> Lambda::operator[] (const int i)
{
return lambda[i];
}
inline const DP* Lambda::operator[] (const int i) const
//inline const Vect<DP> Lambda::operator[] (const int i) const
{
return lambda[i];
}
//****************************************************************************
// Objects in class Ix2_Offsets carry Young tableau representations of the Ix2 configurations
/*
class Ix2_Offsets {
public:
Heis_Base base;
Vect<Young_Tableau> Tableau; // vector of pointers to tableaux at each level
long long int type_id;
long long int id; // id number of offset
long long int maxid; // max id number allowable
public:
Ix2_Offsets ();
Ix2_Offsets (const Ix2_Offsets& RefOffset); // copy constructor
Ix2_Offsets (const Heis_Base& RefBase, long long int req_type_id);
Ix2_Offsets (const Heis_Base& RefBase, Vect<int> nparticles); // sets all tableaux to empty ones, with nparticles[] at each level
Ix2_Offsets& operator= (const Ix2_Offsets& RefOffset);
bool operator<= (const Ix2_Offsets& RefOffsets);
bool operator>= (const Ix2_Offsets& RefOffsets);
public:
void Set_to_id (long long int idnr);
void Compute_id ();
void Compute_type_id ();
public:
bool Add_Boxes_From_Lowest (int Nboxes, bool odd_sectors); // adds Nboxes in minimal energy config, all boxes in either even or odd sectors
};
inline long long int Ix2_Offsets_type_id (Vect<int>& nparticles)
{
long long int type_id_here = 0ULL;
for (int i = 0; i < nparticles.size(); ++i)
type_id_here += nparticles[i] * pow_ulli(10ULL, i);
return(type_id_here);
}
long long int Find_idmin (Ix2_Offsets& scan_offsets, int particle_type, int tableau_level, int Row_L_min);
long long int Find_idmax (Ix2_Offsets& scan_offsets, int particle_type, int tableau_level);
*/
//****************************************************************************
// Objects in class Ix2_Offsets_List carry a vector of used Ix2_Offsets
/*
class Ix2_Offsets_List {
public:
int ndef;
Vect<Ix2_Offsets> Offsets;
public:
Ix2_Offsets_List ();
Ix2_Offsets& Return_Offsets (Heis_Base& RefBase, Vect<int> nparticles); // returns the Ix2_Offsets corresponding to nparticles[]/base
Ix2_Offsets& Return_Offsets (Heis_Base& RefBase, long long int req_type_id);
};
*/
//****************************************************************************
// Objects in class Heis_Bethe_State carry all information about an eigenstate
// Derived classes include XXZ_Bethe_State, XXX_Bethe_State, XXZ_gpd_Bethe_State
// These contain subclass-specific functions and data.
class Heis_Bethe_State {
public:
Heis_Chain chain;
Heis_Base base;
//Ix2_Offsets offsets;
//Ix2_Config Ix2;
Vect<Vect<int> > Ix2;
Lambda lambda;
Lambda deviation; // string deviations
Lambda BE; // Bethe equation for relevant rapidity, in the form BE = theta - (1/N)\sum ... - \pi I/N = 0
DP diffsq; // sum of squares of rapidity differences in last iteration
int conv; // convergence status
DP dev; // sum of absolute values of string deviations
int iter; // number of iterations necessary for convergence
int iter_Newton; // number of iterations necessary for convergence (Newton method)
DP E; // total energy
int iK; // K = 2.0*PI * iK/Nsites
DP K; // total momentum
DP lnnorm; // ln of norm of reduced Gaudin matrix
//long long int base_id;
//long long int type_id;
//long long int id;
//long long int maxid;
//int nparticles;
string label;
public:
Heis_Bethe_State ();
Heis_Bethe_State (const Heis_Bethe_State& RefState); // copy constructor
//Heis_Bethe_State (const Heis_Bethe_State& RefState, long long int type_id_ref); // new state with requested type_id
Heis_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
Heis_Bethe_State (const Heis_Chain& RefChain, const Heis_Base& base); // constructor to lowest-energy config with base
//Heis_Bethe_State (const Heis_Chain& RefChain, long long int base_id_ref, long long int type_id_ref);
virtual ~Heis_Bethe_State () {};
public:
int Charge () { return(base.Mdown); };
//void Set_Ix2_Offsets (const Ix2_Offsets& RefOffset); // sets the Ix2 to given offsets
//void Set_to_id (long long int id_ref);
//void Set_to_id (long long int id_ref, Heis_Bethe_State& RefState);
//int Nparticles (); // counts the number of particles in state once Ix2 offsets set (so type_id is correctly set)
//void Set_to_Label (string label_ref, const Ix2_Config& OriginIx2);
void Set_to_Label (string label_ref, const Vect<Vect<int> >& OriginIx2);
void Set_Label_from_Ix2 (const Vect<Vect<int> >& OriginIx2);
bool Check_Symmetry (); // checks whether the I's are symmetrically distributed
void Compute_diffsq (); // \sum BE[j][alpha]^2
void Find_Rapidities (bool reset_rapidities); // Finds the rapidities
void Find_Rapidities_Twisted (bool reset_rapidities, DP twist); // Finds the rapidities with twist added to RHS of logBE
//void BAE_smackdown (DP max_allowed);
//void Solve_BAE_smackdown (DP max_allowed, int maxruns);
void Solve_BAE_bisect (int j, int alpha, DP req_prec, int itermax);
void Iterate_BAE (DP iter_factor); // Finds new set of lambda[j][alpha] from previous one by simple iteration
void Solve_BAE_straight_iter (DP straight_prec, int max_iter_interp, DP iter_factor);
void Solve_BAE_extrap (DP extrap_prec, int max_iter_extrap, DP iter_factor);
void Iterate_BAE_Newton (); // Finds new set of lambda[j][alpha] from previous one by a Newton step
void Solve_BAE_Newton (DP Newton_prec, int max_iter_Newton);
void Solve_BAE_with_silk_gloves (DP silk_prec, int max_iter_silk, DP iter_factor);
void Compute_lnnorm ();
void Compute_Momentum ();
void Compute_All (bool reset_rapidities); // solves BAE, computes E, K and lnnorm
inline bool Set_to_Inner_Skeleton (int iKneeded, const Vect<Vect<int> >& OriginStateIx2)
{
Ix2[0][0] = Ix2[0][1] - 2;
Ix2[0][base.Nrap[0] - 1] = Ix2[0][base.Nrap[0] - 2] + 2;
(*this).Compute_Momentum();
if (base.Nrap[0] == 0) return(false);
if (iKneeded >= iK) Ix2[0][base.Nrap[0]-1] += 2*(iKneeded - iK);
else Ix2[0][0] += 2*(iKneeded - iK);
if (Ix2[0][0] < base.Ix2_min[0] || Ix2[0][base.Nrap[0]-1] > base.Ix2_max[0]) return(false);
(*this).Set_Label_from_Ix2 (OriginStateIx2);
return(true);
}
void Set_to_Outer_Skeleton (const Vect<Vect<int> >& OriginStateIx2) {
Ix2[0][0] = base.Ix2_min[0] - 4;
Ix2[0][base.Nrap[0]-1] = base.Ix2_max[0] + 4;
(*this).Set_Label_from_Ix2 (OriginStateIx2);
};
void Set_to_Closest_Matching_Ix2_fixed_Base (const Heis_Bethe_State& StateToMatch); // defined in Heis.cc
// Virtual functions, all defined in the derived classes
public:
virtual void Set_Free_lambdas() { JSCerror("Heis_Bethe_State::..."); } // sets the rapidities to solutions of BAEs without scattering terms
virtual bool Check_Admissibility(char option) { JSCerror("Heis_Bethe_State::..."); return(false); }
// verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
virtual void Compute_BE (int j, int alpha) { JSCerror("Heis_Bethe_State::..."); }
virtual void Compute_BE () { JSCerror("Heis_Bethe_State::..."); }
virtual DP Iterate_BAE(int i, int alpha) { JSCerror("Heis_Bethe_State::..."); return(0.0);}
virtual bool Check_Rapidities() { JSCerror("Heis_Bethe_State::..."); return(false); }
virtual DP String_delta () { JSCerror("Heis_Bethe_State::..."); return(0.0); }
virtual void Compute_Energy () { JSCerror("Heis_Bethe_State::..."); }
virtual void Build_Reduced_Gaudin_Matrix (SQMat<complex<DP> >& Gaudin_Red) { JSCerror("Heis_Bethe_State::..."); }
};
inline bool Is_Inner_Skeleton (Heis_Bethe_State& State) {
return (State.base.Nrap[0] >= 2 && (State.Ix2[0][0] == State.Ix2[0][1] - 2 || State.Ix2[0][State.base.Nrap[0]-1] == State.Ix2[0][State.base.Nrap[0]-2] + 2));
};
inline bool Is_Outer_Skeleton (Heis_Bethe_State& State) {
return (State.Ix2[0][0] == State.base.Ix2_min[0] - 4 && State.Ix2[0][State.base.Nrap[0]-1] == State.base.Ix2_max[0] + 4);
};
inline bool Force_Descent (char whichDSF, Heis_Bethe_State& ScanState, Heis_Bethe_State& RefState, int desc_type_required, int iKmod, DP Chem_Pot)
{
bool force_descent = false;
// Force descent if energy of ScanState is lower than that of RefState
//if (ScanState.E - RefState.E - (ScanState.base.Mdown - RefState.base.Mdown) < 0.0) return(true);
/*
// We force descent if
// 1) - there exists a higher string whose quantum number is still on 0
// AND - there is at most a single particle-hole in the 0 base level
// AND - either the particle or the hole hasn't yet moved.
if (ScanState.base_id/100000LL > 0) { // there is a higher string
int type0 = ScanState.type_id % 10000;
if (type0 == 0
|| type0 == 101 && ScanState.offsets.Tableau[0].id * ScanState.offsets.Tableau[2].id == 0LL
|| type0 == 110 && ScanState.offsets.Tableau[1].id * ScanState.offsets.Tableau[2].id == 0LL
|| type0 == 1001 && ScanState.offsets.Tableau[0].id * ScanState.offsets.Tableau[3].id == 0LL
|| type0 == 1010 && ScanState.offsets.Tableau[1].id * ScanState.offsets.Tableau[3].id == 0LL) // single p-h pair in base level 0
for (int j = 1; j < ScanState.chain.Nstrings; ++j) {
if (ScanState.base[j] == 1 && ScanState.Ix2[j][0] == 0) {
force_descent = true;
}
}
}
*/
// Force descent if quantum nr distribution is symmetric:
//if (ScanState.Check_Symmetry()) force_descent = true;
//if (desc_type_required > 8 && ScanState.Check_Symmetry()) force_descent = true;
// Force descent for longitudinal if we're at zero or pi momentum:
//ScanState.Compute_Momentum();
//if (whichDSF == 'z' && (ScanState.iK - RefState.iK) % iKmod == 0) force_descent = true;
//if (desc_type_required > 8 && whichDSF == 'z' && (2*(ScanState.iK - RefState.iK) % iKmod == 0)) force_descent = true; // type_req > 8 means that we don't conserve momentum
// Force descent for all DSFs if we're at K = 0 or PI and not conserving momentum upon descent:
if (desc_type_required > 8 && (2*(ScanState.iK - RefState.iK) % iKmod == 0)) force_descent = true; // type_req > 8 means that we don't conserve momentum
//if (force_descent) cout << "Forcing descent on state with label " << ScanState.label << endl;
if (ScanState.chain.Delta > 1.0) {
/*
// Count the nr of holes in one-strings:
int nholes = 0;
for (int i = 0; i < ScanState.base.Nrap[0] - 1; ++i) if (ScanState.Ix2[0][i+1] - ScanState.Ix2[0][i] != 2) nholes++;
if (nholes <= 2) {
if (ScanState.base.Nrap[0] == ScanState.base.Mdown - 2 && ScanState.base.Nrap[1] == 1) force_descent = true;
if (ScanState.base.Nrap[0] == ScanState.base.Mdown - 3 && ScanState.base.Nrap[2] == 1) force_descent = true;
if (ScanState.base.Nrap[0] == ScanState.base.Mdown - 4 && ScanState.base.Nrap[1] == 2) force_descent = true;
}
*/
if (ScanState.label.compare(0, 10, "14x1y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "14x1y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "14x1y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "14x1y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "14x1y1_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "14x1y1_2x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "12x1y2_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "12x1y2_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "12x1y2_0x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "12x1y2_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "12x1y2_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "12x1y2_1x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "12x1y2_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "12x1y2_2x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "12x1y2_2x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "13x2y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "13x2y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "13x2y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "13x2y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "13x2y1_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "13x2y1_2x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "30x1y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "30x1y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "30x1y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "30x1y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "30x1y1_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "30x1y1_2x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "28x1y2_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "28x1y2_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "28x1y2_0x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "28x1y2_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "28x1y2_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "28x1y2_1x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "28x1y2_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "28x1y2_2x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "28x1y2_2x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "29x2y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "29x2y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "29x2y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "29x2y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "29x2y1_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "29x2y1_2x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "46x1y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "46x1y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "46x1y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "46x1y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "46x1y1_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "46x1y1_2x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "44x1y2_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "44x1y2_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "44x1y2_0x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "44x1y2_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "44x1y2_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "44x1y2_1x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "44x1y2_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "44x1y2_2x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "44x1y2_2x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "45x2y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "45x2y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "45x2y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "45x2y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "45x2y1_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "45x2y1_2x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "62x1y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "62x1y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "62x1y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "62x1y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "62x1y1_2x0") == 0) force_descent = true;
//if (ScanState.label.compare(0, 10, "62x1y1_2x1") == 0 && desc_type_required < 2) force_descent = true;
if (ScanState.label.compare(0, 10, "62x1y1_2x1") == 0
&& (desc_type_required == 14 || desc_type_required == 13 || desc_type_required == 11 || desc_type_required == 10)) force_descent = true;
/*
if (ScanState.label.compare(0, 10, "60x1y2_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "60x1y2_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "60x1y2_0x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "60x1y2_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "60x1y2_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "60x1y2_1x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "60x1y2_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "60x1y2_2x1") == 0 && desc_type_required < 2) force_descent = true;
if (ScanState.label.compare(0, 10, "60x1y2_2x2") == 0 && desc_type_required < 2) force_descent = true;
if (ScanState.label.compare(0, 10, "61x2y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "61x2y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "61x2y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "61x2y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "61x2y1_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "61x2y1_2x1") == 0 && desc_type_required < 2) force_descent = true;
*/
if (ScanState.label.compare(0, 11, "126x1y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 11, "126x1y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 11, "126x1y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 11, "126x1y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 11, "126x1y1_2x0") == 0) force_descent = true;
//if (ScanState.label.compare(0, 11, "126x1y1_2x1") == 0 && desc_type_required < 2) force_descent = true;
if (ScanState.label.compare(0, 11, "126x1y1_2x1") == 0
&& (desc_type_required == 14 || desc_type_required == 13 || desc_type_required == 11 || desc_type_required == 10)) force_descent = true;
/*
if (ScanState.label.compare(0, 10, "124x1y2_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "124x1y2_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "124x1y2_0x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "124x1y2_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "124x1y2_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "124x1y2_1x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "124x1y2_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "124x1y2_2x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "124x1y2_2x2") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "125x2y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "125x2y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "125x2y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "125x2y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "125x2y1_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 10, "125x2y1_2x1") == 0) force_descent = true;
*/
if (ScanState.label.compare(0, 11, "254x1y1_0x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 11, "254x1y1_0x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 11, "254x1y1_1x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 11, "254x1y1_1x1") == 0) force_descent = true;
if (ScanState.label.compare(0, 11, "254x1y1_2x0") == 0) force_descent = true;
if (ScanState.label.compare(0, 11, "254x1y1_2x1") == 0 && desc_type_required < 2) force_descent = true;
// Do not force descent a state with rapidities outside of fundamental interval:
/*
for (int j = 0; j < ScanState.chain.Nstrings; ++j) {
// Logic: allow rapidities -PI/2 <= lambda <= PI/2 (including boundaries)
if (ScanState.base.Nrap[j] > 0 &&
(ScanState.lambda[j][0] < -PI/2 || ScanState.lambda[j][ScanState.base.Nrap[j] - 1] > PI/2))
force_descent = false;
// rapidities should also be ordered as the quantum numbers:
for (int alpha = 1; alpha < ScanState.base.Nrap[j]; ++alpha)
if (ScanState.lambda[j][alpha - 1] >= ScanState.lambda[j][alpha])
force_descent = false;
}
*/
//if (force_descent) cout << "Forcing descent on state with label " << ScanState.label << endl;
} // if Delta > 1
//if (ScanState.base.Nrap[0] == ScanState.base.Mdown - 2 && ScanState.base.Nrap[1] == 1 && ScanState.Ix2[1][0] == 0) force_descent = true;
//if (ScanState.base.Nrap[0] == ScanState.base.Mdown - 3 && ScanState.base.Nrap[2] == 1 && ScanState.Ix2[2][0] == 0) force_descent = true;
//if (ScanState.base.Nrap[0] == ScanState.base.Mdown - 4 && ScanState.base.Nrap[1] == 2 && ScanState.Ix2[1][0] == -1 && ScanState.Ix2[1][1] == 1) force_descent = true;
return(force_descent);
}
std::ostream& operator<< (std::ostream& s, const Heis_Bethe_State& state);
//****************************************************************************
// Objects in class XXZ_Bethe_State carry all extra information pertaining to XXZ gapless
class XXZ_Bethe_State : public Heis_Bethe_State {
public:
Lambda sinhlambda;
Lambda coshlambda;
Lambda tanhlambda;
public:
XXZ_Bethe_State ();
XXZ_Bethe_State (const XXZ_Bethe_State& RefState); // copy constructor
XXZ_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
XXZ_Bethe_State (const Heis_Chain& RefChain, const Heis_Base& base); // constructor to lowest-energy config with base
//XXZ_Bethe_State (const Heis_Chain& RefChain, long long int base_id_ref, long long int type_id_ref); // constructor to lowest-energy config with bas
public:
XXZ_Bethe_State& operator= (const XXZ_Bethe_State& RefState);
public:
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
void Compute_sinhlambda();
void Compute_coshlambda();
void Compute_tanhlambda();
bool Check_Admissibility(char option); // verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
void Compute_BE (int j, int alpha);
void Compute_BE ();
DP Iterate_BAE(int i, int j);
bool Check_Rapidities(); // checks that all rapidities are not nan
DP String_delta ();
void Compute_Energy ();
//void Compute_Momentum ();
void Build_Reduced_Gaudin_Matrix (SQMat<complex<DP> >& Gaudin_Red);
// XXZ specific functions:
public:
};
XXZ_Bethe_State Add_Particle_at_Center (const XXZ_Bethe_State& RefState);
XXZ_Bethe_State Remove_Particle_at_Center (const XXZ_Bethe_State& RefState);
//****************************************************************************
// Objects in class XXX_Bethe_State carry all extra information pertaining to XXX antiferromagnet
class XXX_Bethe_State : public Heis_Bethe_State {
public:
XXX_Bethe_State ();
XXX_Bethe_State (const XXX_Bethe_State& RefState); // copy constructor
XXX_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
XXX_Bethe_State (const Heis_Chain& RefChain, const Heis_Base& base); // constructor to lowest-energy config with base
//XXX_Bethe_State (const Heis_Chain& RefChain, long long int base_id_ref, long long int type_id_ref); // constructor to lowest-energy config with base
public:
XXX_Bethe_State& operator= (const XXX_Bethe_State& RefState);
public:
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
bool Check_Admissibility(char option); // verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
void Compute_BE (int j, int alpha);
void Compute_BE ();
DP Iterate_BAE(int i, int j);
bool Check_Rapidities(); // checks that all rapidities are not nan
DP String_delta ();
void Compute_Energy ();
//void Compute_Momentum ();
void Build_Reduced_Gaudin_Matrix (SQMat<complex<DP> >& Gaudin_Red);
// XXX specific functions
public:
bool Check_Finite_rap ();
};
XXX_Bethe_State Add_Particle_at_Center (const XXX_Bethe_State& RefState);
XXX_Bethe_State Remove_Particle_at_Center (const XXX_Bethe_State& RefState);
//****************************************************************************
// Objects in class XXZ_gpd_Bethe_State carry all extra information pertaining to XXZ gapped antiferromagnets
class XXZ_gpd_Bethe_State : public Heis_Bethe_State {
public:
Lambda sinlambda;
Lambda coslambda;
Lambda tanlambda;
public:
XXZ_gpd_Bethe_State ();
XXZ_gpd_Bethe_State (const XXZ_gpd_Bethe_State& RefState); // copy constructor
XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, int M); // constructor to ground-state configuration
XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, const Heis_Base& base); // constructor to lowest-energy config with base
//XXZ_gpd_Bethe_State (const Heis_Chain& RefChain, long long int base_id_ref, long long int type_id_ref); // constructor to lowest-energy config with base
public:
XXZ_gpd_Bethe_State& operator= (const XXZ_gpd_Bethe_State& RefState);
public:
void Set_Free_lambdas(); // sets the rapidities to solutions of BAEs without scattering terms
void Compute_sinlambda();
void Compute_coslambda();
void Compute_tanlambda();
int Weight(); // weight function for contributions cutoff
bool Check_Admissibility(char option); // verifies that we don't have a symmetrical Ix2 config with a Ix2 == 0 for a string of even length >= 2.
void Compute_BE (int j, int alpha);
void Compute_BE ();
DP Iterate_BAE(int i, int j);
void Iterate_BAE_Newton();
bool Check_Rapidities(); // checks that all rapidities are not nan and are in interval ]-PI/2, PI/2]
DP String_delta ();
void Compute_Energy ();
//void Compute_Momentum ();
void Build_Reduced_Gaudin_Matrix (SQMat<complex<DP> >& Gaudin_Red);
// XXZ_gpd specific functions
public:
};
XXZ_gpd_Bethe_State Add_Particle_at_Center (const XXZ_gpd_Bethe_State& RefState);
XXZ_gpd_Bethe_State Remove_Particle_at_Center (const XXZ_gpd_Bethe_State& RefState);
//***********************************************
// Function declarations
// in M_vs_H.cc
DP Ezero (DP Delta, int N, int M);
DP H_vs_M (DP Delta, int N, int M);
DP HZmin (DP Delta, int N, int M, Vect_DP& Ezero_ref);
int M_vs_H (DP Delta, int N, DP HZ);
DP X_avg (char xyorz, DP Delta, int N, int M);
DP Chemical_Potential (const Heis_Bethe_State& RefState);
DP Particle_Hole_Excitation_Cost (char whichDSF, Heis_Bethe_State& AveragingState);
//DP Sumrule_Factor (char whichDSF, Heis_Bethe_State& RefState, DP Chem_Pot, bool fixed_iK, int iKneeded);
DP Sumrule_Factor (char whichDSF, Heis_Bethe_State& RefState, DP Chem_Pot, int iKmin, int iKmax);
void Evaluate_F_Sumrule (string prefix, char whichDSF, const Heis_Bethe_State& RefState, DP Chem_Pot, int iKmin, int iKmax);
complex<DP> ln_Sz_ME (XXZ_Bethe_State& A, XXZ_Bethe_State& B);
complex<DP> ln_Smin_ME (XXZ_Bethe_State& A, XXZ_Bethe_State& B);
complex<DP> ln_Sz_ME (XXX_Bethe_State& A, XXX_Bethe_State& B);
complex<DP> ln_Smin_ME (XXX_Bethe_State& A, XXX_Bethe_State& B);
// From Antoine Klauser:
complex<DP> ln_Szz_ME (XXX_Bethe_State& A, XXX_Bethe_State& B);
complex<DP> ln_Szm_p_Smz_ME (XXX_Bethe_State& A, XXX_Bethe_State& B);
complex<DP> ln_Smm_ME (XXX_Bethe_State& A, XXX_Bethe_State& B);
complex<DP> ln_Sz_ME (XXZ_gpd_Bethe_State& A, XXZ_gpd_Bethe_State& B);
complex<DP> ln_Smin_ME (XXZ_gpd_Bethe_State& A, XXZ_gpd_Bethe_State& B);
// The following functions have become member functions.
//DP String_delta (XXZ_Bethe_State& state);
//DP String_delta (XXX_Bethe_State& state);
//DP String_delta (XXZ_gpd_Bethe_State& state);
//DP Compute_Form_Factor_Entry (char whichDSF, Heis_Bethe_State& LeftState, Heis_Bethe_State& RefState, DP Chem_Pot, fstream& DAT_outfile);
//DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, XXZ_Bethe_State& LeftState,
// XXZ_Bethe_State& RefState, DP Chem_Pot, fstream& DAT_outfile);
DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, XXZ_Bethe_State& LeftState,
XXZ_Bethe_State& RefState, DP Chem_Pot, stringstream& DAT_outfile);
//DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, XXX_Bethe_State& LeftState,
// XXX_Bethe_State& RefState, DP Chem_Pot, fstream& DAT_outfile);
DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, XXX_Bethe_State& LeftState,
XXX_Bethe_State& RefState, DP Chem_Pot, stringstream& DAT_outfile);
//DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, XXZ_gpd_Bethe_State& LeftState,
// XXZ_gpd_Bethe_State& RefState, DP Chem_Pot, fstream& DAT_outfile);
DP Compute_Matrix_Element_Contrib (char whichDSF, int iKmin, int iKmax, XXZ_gpd_Bethe_State& LeftState,
XXZ_gpd_Bethe_State& RefState, DP Chem_Pot, stringstream& DAT_outfile);
// For geometric quench:
complex<DP> ln_Overlap (XXX_Bethe_State& A, XXX_Bethe_State& B);
void Scan_Heis_Geometric_Quench (DP Delta, int N_1, int M, long long int base_id_1, long long int type_id_1, long long int id_1,
int N_2, int iKmin, int iKmax, int Max_Secs, bool refine);
} // namespace JSC
#endif
-32
View File
@@ -1,32 +0,0 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
-----------------------------------------------------------
File: JSC_Infprec.h
Purpose: Declarations for infinite precision arithmetic classes.
***********************************************************/
#ifndef _JSC_INFPREC_
#define _JSC_INFPREC_
namespace JSC {
class infprec_int {
private:
int nintrep; // number of integers used in representation
int baseint; // fundamental int
Vect<unsigned int> xint; // extra integers
}
} // namespace JSC
#endif
-440
View File
@@ -1,440 +0,0 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
-----------------------------------------------------------
File: JSC_Matrix.h
Purpose: Declares square matrix class.
***********************************************************/
#ifndef _MATRIX_
#define _MATRIX_
namespace JSC {
// CLASS DEFINITIONS
template <class T>
class SQMat {
private:
int dim;
T** M;
public:
SQMat (int N); // initializes all elements of this n by n matrix to zero
SQMat (const SQMat& rhs); // copy constructor
SQMat (const T& a, int N); // initialize to diagonal matrix with value a (NOT like in NR !!!)
SQMat (const SQMat& a, const SQMat& b); // initialize to tensor product of a and b
SQMat (const SQMat& a, int row_id, int col_id); // init by cutting row row_id and col col_id
void Print ();
SQMat& operator= (const SQMat& rhs); // assignment
SQMat& operator= (const T& a); // assign 1 to diagonal elements (NOT like in NR !!!)
inline T* operator[] (const int i); // subscripting: pointer to row i
inline const T* operator[] (const int i) const;
SQMat& operator+= (const T& a);
SQMat& operator+= (const SQMat& a);
SQMat& operator-= (const T& a);
SQMat& operator-= (const SQMat& a);
SQMat& operator*= (const T& a);
SQMat& operator*= (const SQMat& a);
inline int size() const;
~SQMat();
};
template <class T>
SQMat<T>::SQMat (int N) : dim(N) , M(new T*[N])
{
M[0] = new T[N*N];
for (int i = 1; i < N; i++) M[i] = M[i-1] + N;
}
template <class T>
SQMat<T>::SQMat (const SQMat& rhs) : dim(rhs.dim) , M(new T*[dim])
{
int i,j;
M[0] = new T[dim*dim];
for (i = 1; i < dim; i++) M[i] = M[i-1] + dim;
for (i = 0; i < dim; i++)
for (j = 0; j < dim; j++) M[i][j] = rhs[i][j];
}
template <class T>
SQMat<T>::SQMat (const T& a, int N) : dim(N) , M(new T*[dim])
{
int i, j;
M[0] = new T[dim*dim];
for (i = 1; i < dim; i++) M[i] = M[i-1] + dim;
for (i = 0; i < dim; i++) {
for (j = 0; j < dim; j++) M[i][j] = T(0);
M[i][i] = a;
}
}
template <class T>
SQMat<T>::SQMat (const SQMat& a, const SQMat& b) : dim (a.dim * b.dim) , M(new T*[a.dim * b.dim])
{
M[0] = new T[a.dim * b.dim * a.dim * b.dim];
for (int i = 1; i < a.dim * b.dim; ++i) M[i] = M[i-1] + a.dim * b.dim;
for (int i1 = 0; i1 < a.dim; ++i1) {
for (int i2 = 0; i2 < a.dim; ++i2) {
for (int j1 = 0; j1 < b.dim; ++j1) {
for (int j2 = 0; j2 < b.dim; ++j2) {
M[i1 * (b.dim) + j1][i2 * (b.dim) + j2] = a[i1][i2] * b[j1][j2];
}
}
}
}
}
template <class T>
SQMat<T>::SQMat (const SQMat&a, int row_id, int col_id) : dim (a.dim - 1) , M(new T*[dim])
{
if (dim == 0) {
JSCerror("Error: chopping a row and col from size one matrix.");
exit(1);
}
M[0] = new T[dim * dim];
for (int i = 1; i < dim; ++i) M[i] = M[i-1] + dim;
for (int i = 0; i < row_id; ++i)
for (int j = 0; j < col_id; ++j) M[i][j] = a[i][j];
for (int i = row_id; i < dim; ++i)
for (int j = 0; j < col_id; ++j) M[i][j] = a[i+1][j];
for (int i = 0; i < row_id; ++i)
for (int j = col_id; j < dim; ++j) M[i][j] = a[i][j+1];
for (int i = row_id; i < dim; ++i)
for (int j = col_id; j < dim; ++j) M[i][j] = a[i+1][j+1];
}
// operators
template <class T>
void SQMat<T>::Print ()
{
cout << endl;
for (int i = 0; i < dim; ++i) {
for (int j = 0; j < dim; ++j) cout << M[i][j] << " ";
cout << endl;
}
cout << endl;
}
template <class T>
SQMat<T>& SQMat<T>::operator= (const SQMat<T>& rhs)
{
if (this != &rhs) {
if (dim != rhs.dim) {
JSCerror("Assignment between matrices of different dimensions. Bailing out.");
exit(1);
}
for (int i = 0; i < dim; ++i)
for (int j = 0; j < dim; ++j) M[i][j] = rhs[i][j];
}
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator= (const T& a)
{
for (int i = 0; i < dim; ++i) {
for (int j = 0; j < dim; ++j)
M[i][j] = T(0);
M[i][i] = a;
}
return *this;
}
template <class T>
inline T* SQMat<T>::operator[] (const int i)
{
return M[i];
}
template <class T>
inline const T* SQMat<T>::operator[] (const int i) const
{
return M[i];
}
template <class T>
SQMat<T>& SQMat<T>::operator+= (const T& a)
{
for (int i = 0; i < dim; ++i) M[i][i] += a;
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator+= (const SQMat<T>& a)
{
if (dim != a.dim) {
JSCerror("Incompatible matrix sizes in matrix operator +.");
exit(1);
}
for (int i = 0; i < dim; ++i) {
for (int j = 0; j < dim; ++j) {
M[i][j] += a[i][j];
}
}
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator-= (const T& a)
{
for (int i = 0; i < dim; ++i) M[i][i] -= a;
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator-= (const SQMat<T>& a)
{
if (dim != a.dim) {
JSCerror("Incompatible matrix sizes in matrix operator +.");
exit(1);
}
for (int i = 0; i < dim; ++i) {
for (int j = 0; j < dim; ++j) {
M[i][j] -= a[i][j];
}
}
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator*= (const T& a)
{
for (int i = 0; i < dim; ++i) for (int j = 0; j < dim; ++j) M[i][j] *= a;
return *this;
}
template <class T>
SQMat<T>& SQMat<T>::operator*= (const SQMat<T>& a)
{
if (dim != a.dim) {
JSCerror("Incompatible matrix sizes in matrix operator *.");
exit(1);
}
SQMat<T> leftarg(*this); // use copy constructor.
for (int i = 0; i < dim; ++i) {
for (int j = 0; j < dim; ++j) {
M[i][j] = 0.0;
for (int k = 0; k < dim; ++k) {
M[i][j] += leftarg[i][k] * a[k][j];
}
}
}
return *this;
}
template <class T>
inline int SQMat<T>::size() const
{
return dim;
}
template <class T>
SQMat<T>::~SQMat()
{
if (M != 0) {
delete[] (M[0]);
delete[] (M);
}
}
//*****************************
template <class T>
class RecMat {
private:
int nrows;
int ncols;
T** M;
public:
RecMat (int Nrows, int Ncols); // initializes all elements of this n by n matrix to zero
RecMat (const T& a, int Nrows, int Ncols);
RecMat (const RecMat& rhs); // copy constructor
void Print ();
RecMat& operator= (const RecMat& rhs); // assignment
inline T* operator[] (const int i); // subscripting: pointer to row i
inline const T* operator[] (const int i) const;
inline int nr_rows() const;
inline int nr_cols() const;
~RecMat();
};
template <class T>
RecMat<T>::RecMat (int Nrows, int Ncols) : nrows(Nrows), ncols(Ncols), M(new T*[Nrows])
{
M[0] = new T[Nrows*Ncols];
for (int i = 1; i < Nrows; i++) M[i] = M[i-1] + Ncols;
for (int i = 0; i < Nrows; i++) for (int j = 0; j < Ncols; j++) M[i][j] = T(0);
}
template <class T>
RecMat<T>::RecMat (const T& a, int Nrows, int Ncols) : nrows(Nrows), ncols(Ncols), M(new T*[Nrows])
{
M[0] = new T[Nrows*Ncols];
for (int i = 1; i < Nrows; i++) M[i] = M[i-1] + Ncols;
for (int i = 0; i < Nrows; i++) for (int j = 0; j < Ncols; j++) {
if (i == j) M[i][i] = a;
else M[i][j] = T(0);
}
}
template <class T>
RecMat<T>::RecMat (const RecMat& rhs) : nrows(rhs.nrows), ncols(rhs.ncols), M(new T*[nrows])
{
int i,j;
M[0] = new T[nrows*ncols];
for (i = 1; i < nrows; i++) M[i] = M[i-1] + ncols;
for (i = 0; i < nrows; i++)
for (j = 0; j < ncols; j++) M[i][j] = rhs[i][j];
}
// operators
template <class T>
void RecMat<T>::Print ()
{
cout << endl;
for (int i = 0; i < nrows; ++i) {
for (int j = 0; j < ncols; ++j) cout << M[i][j] << " ";
cout << endl;
}
cout << endl;
}
template <class T>
RecMat<T>& RecMat<T>::operator= (const RecMat<T>& rhs)
{
if (this != &rhs) {
if (nrows != rhs.nrows || ncols != rhs.ncols) {
if (M != 0) {
delete[] (M[0]);
delete[] (M);
}
nrows = rhs.nrows;
ncols = rhs.ncols;
M = new T*[nrows];
M[0] = new T[nrows * ncols];
}
for (int i = 0; i < nrows; ++i)
for (int j = 0; j < ncols; ++j) M[i][j] = rhs[i][j];
}
return *this;
}
template <class T>
inline T* RecMat<T>::operator[] (const int i)
{
return M[i];
}
template <class T>
inline const T* RecMat<T>::operator[] (const int i) const
{
return M[i];
}
template <class T>
inline int RecMat<T>::nr_rows() const
{
return nrows;
}
template <class T>
inline int RecMat<T>::nr_cols() const
{
return ncols;
}
template <class T>
inline std::ostream& operator<< (std::ostream& s, const RecMat<T>& matrix)
{
for (int i = 0; i < matrix.nr_rows(); ++i) {
for (int j = 0; j < matrix.nr_cols(); ++j) s << matrix[i][j] << " ";
s << endl;
}
return (s);
}
template <class T>
RecMat<T>::~RecMat()
{
if (M != 0) {
delete[] (M[0]);
delete[] (M);
}
}
// TYPEDEFS:
typedef JSC::SQMat<DP> SQMat_DP;
typedef JSC::SQMat<complex<double> > SQMat_CX;
// FUNCTION DEFINITIONS
// Functions in src/MATRIX directory
DP det_LU (SQMat_DP a);
DP lndet_LU (SQMat_DP a);
complex<DP> lndet_LU_dstry (SQMat_DP& a);
complex<DP> det_LU_CX (SQMat_CX a);
complex<DP> lndet_LU_CX (SQMat_CX a);
complex<DP> lndet_LU_CX_dstry (SQMat_CX& a);
void eigsrt (Vect_DP& d, SQMat_DP& v);
void balanc (SQMat_DP& a);
void elmhes (SQMat_DP& a);
void gaussj (SQMat_DP& a, SQMat_DP& b);
void hqr (SQMat_DP& a, Vect_CX& wri);
void jacobi (SQMat_DP& a, Vect_DP& d, SQMat_DP& v, int& nrot);
void lubksb (SQMat_DP& a, Vect_INT& indx, Vect_DP& b);
void lubksb_CX (SQMat_CX& a, Vect_INT& indx, Vect_CX& b);
void ludcmp (SQMat_DP& a, Vect_INT& indx, DP& d);
void ludcmp_CX (SQMat_CX& a, Vect_INT& indx, DP& d);
DP pythag(DP a, DP b);
void tqli(Vect_DP& d, Vect_DP& e, SQMat_DP& z);
void tred2 (SQMat_DP& a, Vect_DP& d, Vect_DP& e);
} // namespace JSC
#endif
-36
View File
@@ -1,36 +0,0 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
-----------------------------------------------------------
File: JSC_NRG.h
Purpose: Declares NRG-related classes and functions.
***********************************************************/
#ifndef _NRG_
#define _NRG_
#include "JSC.h"
namespace JSC {
DP K_Weight_integrand (Vect_DP args); // weighing function for state selection
//void Select_States_for_NRG (DP c_int, DP L, int N, int iKmin, int iKmax, int Nstates_required, bool symmetric_states, int iKmod,
// int weighing_option, DP (*weight_integrand_fn) (Vect_DP), Vect_DP& args_to_weight_integrand);
void Select_States_for_NRG (DP c_int, DP L, int N, int iKmin, int iKmax, int Nstates_required, bool symmetric_states, int iKmod,
//int weighing_option, DP (*weight_integrand_fn) (Vect_DP), Vect_DP& args_to_weight_integrand)
int weighing_option, Vect<complex <DP> >& FT_of_potential);
void Build_DFF_Matrix_Block_for_NRG (DP c_int, DP L, int N, int iKmin, int iKmax, int Nstates_required, bool symmetric_states, int iKmod,
int weighing_option, int label_left_begin, int label_left_end, int label_right_begin, int label_right_end,
int block_option, DP* DFF_block_1, DP* DFF_block_2, Vect_DP Kweight);
}
#endif // _NRG_
-1263
View File
File diff suppressed because it is too large Load Diff
-86
View File
@@ -1,86 +0,0 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
-----------------------------------------------------------
File: JSC_XXZ_h0.h
Purpose: Declares classes for XXZ in zero field: quantum group stuff.
***********************************************************/
#ifndef _XXZ_h0_
#define _XXZ_h0_
#include "JSC.h"
//const DP default_req_prec = 1.0e-14;
//const int default_max_rec = 10;
namespace JSC {
/*
inline DP Integrand_xi_11 (Vect_DP args)
{
// args[0] corresponds to t, args[1] to rho, args[2] to xi
//return((exp(args[0]) * sinh(args[0]) * cos(4.0 * args[0] * args[1])/(2.0 * pow(cosh(args[0]), 2.0)) + 2.0 * pow(sin(2.0 * args[0] * args[1]), 2.0))/args[0]);
return((sinh(args[0]*(1.0 + args[2])) * sinh(args[0]) * cos(4.0 * args[0] * args[1])/(2.0 * sinh(args[0] * args[2]) * pow(cosh(args[0]), 2.0))
+ 2.0 * pow(sin(2.0 * args[0] * args[1]), 2.0))/args[0]);
}
inline DP Integrand_xi_12 (Vect_DP args)
{
DP expm2t = exp(-2.0*args[0]);
DP expm2txi = exp(-2.0*args[0]*args[2]);
//return(cos(4.0 * args[0] * args[1]) * expm2t * (3.0 + expm2t)/ (args[0] * (1.0 + expm2t) * (1.0 + expm2t)));
return(cos(4.0 * args[0] * args[1]) * (expm2t * (3.0 * (1.0 + expm2txi) + expm2t) + expm2txi) / (args[0] * (1.0 - expm2txi) * (1.0 + expm2t) * (1.0 + expm2t)));
}
*/
/*
inline DP Integrand_xi_2 (Vect_DP args)
{
DP answer = 0.0;
if (args[0] < 1.0)
//answer = exp(args[0]) * pow(sin(2.0 * args[0] * args[1]), 2.0)/(args[0] * sinh(args[0]) * pow(cosh(args[0]), 2.0));
answer = sinh(args[0] * (args[2] + 1.0)) * pow(sin(2.0 * args[0] * args[1]), 2.0)/(args[0] * sinh(args[2] * args[0]) * sinh(args[0]) * pow(cosh(args[0]), 2.0));
else if (args[0] >= 1.0) {
DP expm2t = exp(-2.0 * args[0]);
DP expm2txi = exp(-2.0*args[0]*args[2]);
//answer = 8.0 * expm2t * pow(sin(2.0 * args[0] * args[1]), 2.0)/(args[0] * (1.0 - expm2t) * (1.0 + expm2t) * (1.0 + expm2t));
answer = 8.0 * ((1.0 - expm2t*expm2txi)/(1.0 - expm2t*expm2txi)) * expm2t *
pow(sin(2.0 * args[0] * args[1]), 2.0)/(args[0] * (1.0 - expm2t) * (1.0 + expm2t) * (1.0 + expm2t));
}
return(answer);
}
*/
DP I_xi_integral (DP xi, DP rho, DP req_prec, int max_nr_pts);
/********************* TWO SPINONS ********************/
DP Szz_XXZ_h0_2spinons (DP k, DP omega, Integral_table Itable);
DP Szz_XXZ_h0_2spinons (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_alt (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_omega (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_omega_alt (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_intomega (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_intomega_alt (Vect_DP args, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_check_sumrule (DP Delta, DP req_prec, int max_nr_pts, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_check_sumrule_alt (DP Delta, DP req_prec, int max_nr_pts, Integral_table Itable);
DP Fixed_k_sumrule_omega_Szz_XXZ_h0_N (DP Delta, DP k);
DP GSE_XXZ_h0 (DP Delta, DP req_prec, int max_nr_pts);
DP Fixed_k_sumrule_omega_Szz_XXZ_h0 (DP Delta, DP k, DP req_prec, int max_nr_pts);
DP Szz_XXZ_h0_2spinons_check_fixed_k_Szz_sumrule (DP Delta, DP k, DP req_prec, int max_nr_pts, Integral_table Itable);
DP Szz_XXZ_h0_2spinons_check_fixed_k_Szz_sumrule_alt (DP Delta, DP k, DP req_prec, int max_nr_pts, Integral_table Itable);
//******************************** Functions to produce files similar to ABACUS **********************************
void Produce_Szz_XXZ_h0_2spinons_file (DP Delta, int N, int Nomega, DP omegamax, Integral_table Itable);
void Produce_Szz_XXZ_h0_2spinons_fixed_K_file (DP Delta, DP Kover2PI, int Nomega, Integral_table Itable);
} // namespace JSC
#endif
-485
View File
@@ -1,485 +0,0 @@
/**********************************************************
This software is part of J.-S. Caux's ABACUS library.
Copyright (c).
-----------------------------------------------------------
File: JSC_util.h
Purpose: Defines basic math functions.
***********************************************************/
#ifndef _JSC_UTIL_H_
#define _JSC_UTIL_H_
#include "JSC.h"
using namespace std;
typedef double DP;
// Global constants
const double PI = 3.141592653589793238462643;
const double sqrtPI = sqrt(PI);
const double twoPI = 2.0*PI;
const double logtwoPI = log(twoPI);
const double Euler_Mascheroni = 0.577215664901532860606;
const double Gamma_min_0p5 = -2.0 * sqrt(PI);
const complex<double> II(0.0,1.0); // Shorthand for i
const DP MACHINE_EPS = numeric_limits<DP>::epsilon();
const DP MACHINE_EPS_SQ = pow(MACHINE_EPS, 2.0);
// Now for some basic math utilities:
namespace JSC {
// File checks:
inline bool file_exists (const char* filename)
{
fstream file;
file.open(filename);
bool exists = !file.fail();
file.close();
return(exists);
}
// Error handler:
inline void JSCerror (const string error_text)
// my error handler
{
cerr << "Run-time error... " << endl;
cerr << error_text << endl;
cerr << "Exiting to system..." << endl;
exit(1);
}
struct Divide_by_zero {};
// Basics: min, max, fabs
template<class T>
inline const T max (const T& a, const T& b) { return a > b ? (a) : (b); }
template<class T>
inline const T min (const T& a, const T& b) { return a > b ? (b) : (a); }
template<class T>
inline const T fabs (const T& a) { return a >= 0 ? (a) : (-a); }
inline long long int pow_lli (const long long int& base, const int& exp)
{
long long int answer = base;
if (exp == 0) answer = 1LL;
else for (int i = 1; i < exp; ++i) answer *= base;
return(answer);
}
inline unsigned long long int pow_ulli (const unsigned long long int& base, const int& exp)
{
unsigned long long int answer = base;
if (exp == 0) answer = 1ULL;
for (int i = 1; i < exp; ++i) answer *= base;
return(answer);
}
inline int fact (const int& N)
{
int ans = 0;
if (N < 0) {
cerr << "Error: factorial of negative number. Exited." << endl;
exit(1);
}
else if ( N == 1 || N == 0) ans = 1;
else ans = N * fact(N-1);
return(ans);
}
inline DP ln_fact (const int& N)
{
DP ans = 0.0;
if (N < 0) {
cerr << "Error: factorial of negative number. Exited." << endl;
exit(1);
}
else if ( N == 1 || N == 0) ans = 0.0;
else ans = log(DP(N)) + ln_fact(N-1);
return(ans);
}
inline long long int fact_lli (const int& N)
{
long long int ans = 0;
if (N < 0) {
cerr << "Error: factorial of negative number. Exited." << endl;
exit(1);
}
else if ( N == 1 || N == 0) ans = 1;
else ans = fact_lli(N-1) * N;
return(ans);
}
inline long long int fact_ulli (const int& N)
{
unsigned long long int ans = 0;
if (N < 0) {
cerr << "Error: factorial of negative number. Exited." << endl;
exit(1);
}
else if ( N == 1 || N == 0) ans = 1;
else ans = fact_ulli(N-1) * N;
return(ans);
}
inline int choose (const int& N1, const int& N2)
{
// returns N1 choose N2
int ans = 0;
if (N1 < N2) {
cout << "Error: N1 smaller than N2 in choose. Exited." << endl;
exit(1);
}
else if (N1 == N2) ans = 1;
else if (N1 < 12) ans = fact(N1)/(fact(N2) * fact(N1 - N2));
else {
ans = 1;
int mult = N1;
while (mult > max(N2, N1 - N2)) ans *= mult--;
ans /= fact(min(N2, N1 - N2));
}
return(ans);
}
inline DP ln_choose (const int& N1, const int& N2)
{
// returns the log of N1 choose N2
DP ans = 0.0;
if (N1 < N2) {
cout << "Error: N1 smaller than N2 in choose. Exited." << endl;
exit(1);
}
else if (N1 == N2) ans = 0.0;
else ans = ln_fact(N1) - ln_fact(N2) - ln_fact(N1 - N2);
return(ans);
}
inline long long int choose_lli (const int& N1, const int& N2)
{
// returns N1 choose N2
long long int ans = 0;
if (N1 < N2) {
cout << "Error: N1 smaller than N2 in choose. Exited." << endl;
exit(1);
}
else if (N1 == N2) ans = 1;
else if (N1 < 12) ans = fact_lli(N1)/(fact_lli(N2) * fact_lli(N1 - N2));
else {
// Make sure that N2 is less than or equal to N1/2; if not, just switch...
int N2_min = min(N2, N1 - N2);
ans = 1;
for (int i = 0; i < N2_min; ++i) {
ans *= (N1 - i);
ans /= i + 1;
}
}
return(ans);
}
inline unsigned long long int choose_ulli (const int& N1, const int& N2)
{
// returns N1 choose N2
unsigned long long int ans = 0;
if (N1 < N2) {
cout << "Error: N1 smaller than N2 in choose. Exited." << endl;
exit(1);
}
else if (N1 == N2) ans = 1;
else if (N1 < 12) ans = fact_ulli(N1)/(fact_ulli(N2) * fact_ulli(N1 - N2));
else {
// Make sure that N2 is less than or equal to N1/2; if not, just switch...
int N2_min = min(N2, N1 - N2);
ans = 1;
for (int i = 0; i < N2_min; ++i) {
ans *= (N1 - i);
ans /= i + 1;
}
}
return(ans);
}
inline DP SIGN (const DP &a, const DP &b)
{
return b >= 0 ? (a >= 0 ? a : -a) : (a >= 0 ? -a : a);
}
inline DP sign_of (const DP& a)
{
return (a >= 0.0 ? 1.0 : -1.0);
}
inline int sgn_int (const int& a)
{
return (a >= 0) ? 1 : -1;
}
inline int sgn_DP (const DP& a)
{
return (a >= 0) ? 1 : -1;
}
template<class T>
inline void SWAP (T& a, T& b) {T dum = a; a = b; b = dum;}
inline int kronecker (int a, int b)
{
return a == b ? 1 : 0;
}
template<class T>
inline bool is_nan (const T& a)
{
return(!((a < T(0.0)) || (a >= T(0.0))));
}
inline complex<DP> atan_cx(const complex<DP>& x)
{
return(-0.5 * II * log((1.0 + II* x)/(1.0 - II* x)));
}
/**************** Gamma function *******************/
inline complex<double> ln_Gamma (complex<double> z)
{
// Implementation of Lanczos method with g = 9.
// Coefficients from Godfrey 2001.
if (real(z) < 0.5) return(log(PI/(sin(PI*z))) - ln_Gamma(1.0 - z));
else {
complex<double> series = 1.000000000000000174663
+ 5716.400188274341379136/z
- 14815.30426768413909044/(z + 1.0)
+ 14291.49277657478554025/(z + 2.0)
- 6348.160217641458813289/(z + 3.0)
+ 1301.608286058321874105/(z + 4.0)
- 108.1767053514369634679/(z + 5.0)
+ 2.605696505611755827729/(z + 6.0)
- 0.7423452510201416151527e-2 / (z + 7.0)
+ 0.5384136432509564062961e-7 / (z + 8.0)
- 0.4023533141268236372067e-8 / (z + 9.0);
return(0.5 * logtwoPI + (z - 0.5) * log(z + 8.5) - (z + 8.5) + log(series));
}
return(log(0.0)); // never called
}
inline complex<double> ln_Gamma_old (complex<double> z)
{
// Implementation of Lanczos method with g = 9.
// Coefficients from Godfrey 2001.
if (real(z) < 0.5) return(log(PI/(sin(PI*z))) - ln_Gamma(1.0 - z));
else {
int g = 9;
double p[11] = { 1.000000000000000174663,
5716.400188274341379136,
-14815.30426768413909044,
14291.49277657478554025,
-6348.160217641458813289,
1301.608286058321874105,
-108.1767053514369634679,
2.605696505611755827729,
-0.7423452510201416151527e-2,
0.5384136432509564062961e-7,
-0.4023533141268236372067e-8 };
complex<double> z_min_1 = z - 1.0;
complex<double> series = p[0];
for (int i = 1; i < g+2; ++i)
series += p[i]/(z_min_1 + complex<double>(i));
return(0.5 * logtwoPI + (z_min_1 + 0.5) * log(z_min_1 + complex<double>(g) + 0.5) - (z_min_1 + complex<double>(g) + 0.5) + log(series));
}
return(log(0.0)); // never called
}
inline complex<double> ln_Gamma_2 (complex<double> z)
{
// Implementation of Lanczos method with g = 7.
if (real(z) < 0.5) return(log(PI/(sin(PI*z)) - ln_Gamma(1.0 - z)));
else {
int g = 7;
double p[9] = { 0.99999999999980993, 676.5203681218851, -1259.1392167224028,
771.32342877765313, -176.61502916214059, 12.507343278686905,
-0.13857109526572012, 9.9843695780195716e-6, 1.5056327351493116e-7};
complex<double> z_min_1 = z - 1.0;
complex<double> series = p[0];
for (int i = 1; i < g+2; ++i)
series += p[i]/(z_min_1 + complex<double>(i));
return(0.5 * logtwoPI + (z_min_1 + 0.5) * log(z_min_1 + complex<double>(g) + 0.5) - (z_min_1 + complex<double>(g) + 0.5) + log(series));
}
return(log(0.0)); // never called
}
/********** Partition numbers **********/
inline long long int Partition_Function (int n)
{
// Returns the value of the partition function p(n), giving the number of partitions of n into integers.
if (n < 0) JSCerror("Calling Partition_Function for n < 0.");
else if (n == 0 || n == 1) return(1LL);
else if (n == 2) return(2LL);
else if (n == 3) return(3LL);
else { // do recursion using pentagonal numbers
long long int pn = 0LL;
int pentnrplus, pentnrmin; // pentagonal numbers
for (int i = 1; true; ++i) {
pentnrplus = (i * (3*i - 1))/2;
pentnrmin = (i * (3*i + 1))/2;
//cout << "\ti = " << i << "pnrp = " << pentnrplus << "\tpnrm = " << pentnrmin << endl;
if (n - pentnrplus >= 0) pn += (i % 2 ? 1LL : -1LL) * Partition_Function (n - pentnrplus);
if (n - pentnrmin >= 0) pn += (i % 2 ? 1LL : -1LL) * Partition_Function (n - pentnrmin);
else break;
}
return(pn);
}
return(-1LL); // never called
}
/********** Sorting **********/
/*
template<class item_type>
void QuickSort (item_type* a, int l, int r)
{
static item_type m;
static int j;
int i;
if (r > l) {
m = a[r]; i = l-1; j = r;
for (;;) {
while (a[++i] < m);
while (a[--j] > m);
if (i >= j) break;
std::swap(a[i], a[j]);
}
std::swap(a[i], a[r]);
QuickSort(a, l, i-1);
QuickSort(a, i+1, r);
}
}
*/
template <class T>
void QuickSort (T* V, int l, int r)
{
int i = l, j = r;
T pivot = V[l + (r-l)/2];
while (i <= j) {
while (V[i] < pivot) i++;
while (V[j] > pivot) j--;
if (i <= j) {
std::swap(V[i],V[j]);
i++;
j--;
}
};
if (l < j) QuickSort(V, l, j);
if (i < r) QuickSort(V, i, r);
}
/*
template<class item_type>
void QuickSort (item_type* a, int* idx, int l, int r)
{
static item_type m;
static int j;
int i;
if (r > l) {
m = a[r]; i = l-1; j = r;
for (;;) {
while (a[++i] < m);
while (a[--j] > m);
if (i >= j) break;
std::swap(a[i], a[j]);
std::swap(idx[i], idx[j]);
}
std::swap(a[i], a[r]);
std::swap(idx[i], idx[r]);
QuickSort(a, idx, l, i-1);
QuickSort(a, idx, i+1, r);
}
}
*/
template <class T>
void QuickSort (T* V, int* index, int l, int r)
{
int i = l, j = r;
T pivot = V[l + (r-l)/2];
while (i <= j) {
while (V[i] < pivot) i++;
while (V[j] > pivot) j--;
if (i <= j) {
std::swap(V[i],V[j]);
std::swap(index[i],index[j]);
i++;
j--;
}
};
if (l < j) QuickSort(V, index, l, j);
if (i < r) QuickSort(V, index, i, r);
}
} // namespace JSC
#endif // _JS_UTIL_H_