//=============================================================================
/*! clear all the matrix data and set the sizes 0 */
inline void zgsmatrix::clear()
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::clear()" << std::endl;
std::cerr << "# [NOTE] zgsmatrix::clear()" << " An array at " << Array << " is going to be cleared." << std::endl;
#endif//CPPL_VERBOSE
M =N =CAP =VOL=0;
delete [] Array; Array=NULL;
delete [] Indx; Indx=NULL;
delete [] Jndx; Jndx=NULL;
delete [] Rows; Rows=NULL;
delete [] Cols; Cols=NULL;
}
//=============================================================================
/*! change the matrix into a zero matrix */
inline zgsmatrix& zgsmatrix::zero()
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::zero()" << std::endl;
#endif//CPPL_VERBOSE
VOL =0;
for(long i=0; i<M; i++){ Rows[i].clear(); }
for(long j=0; j<M; j++){ Cols[j].clear(); }
return *this;
}
//=============================================================================
/*! change sign(+/-) of the matrix */
inline void zgsmatrix::chsign()
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::chsign()" << std::endl;
#endif//CPPL_VERBOSE
for(long i=0; i<VOL; i++){ Array[i] =-Array[i]; }
}
//=============================================================================
/*! make a deep copy of the matrix */
inline void zgsmatrix::copy(const zgsmatrix& mat)
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::copy(const zgsmatrix&)" << std::endl;
std::cerr << "# [NOTE] zgsmatrix::copy(const zgsmatrix&)" << " A zgsmatrix at " << Array << " is going to be deleted." << std::endl;
#endif//CPPL_VERBOSE
resize(mat.M, mat.N, mat.CAP);
VOL =mat.VOL;
zcopy_(VOL, mat.Array, 1, Array, 1);
for(long i=0; i<VOL; i++){
Indx[i] =mat.Indx[i];
Jndx[i] =mat.Jndx[i];
}
for(long i=0; i<M; i++){ Rows[i] =mat.Rows[i]; }
for(long j=0; j<N; j++){ Cols[j] =mat.Cols[j]; }
#ifdef CPPL_VERBOSE
std::cerr << " Then, a COPY of a zgsmatrix has been cleated at " << Array << "." << std::endl;
#endif//CPPL_VERBOSE
}
//=============================================================================
/*! make a shallow copy of the matrix\n
This function is not designed to be used in project codes. */
inline void zgsmatrix::shallow_copy(const _zgsmatrix& mat)
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::shallow_copy(const _zgsmatrix&)" << std::endl;
std::cerr << "# [NOTE] zgsmatrix::shallow_copy(const _zgsmatrix&)" << " A zgsmatrix at " << Array << " is going to be deleted, " << "and point at " << mat.Array << " instead." << std::endl;
#endif//CPPL_VERBOSE
delete [] Array;
delete [] Indx;
delete [] Jndx;
delete [] Rows;
delete [] Cols;
M =mat.M;
N =mat.N;
CAP =mat.CAP;
VOL =mat.VOL;
Array =mat.Array;
Indx =mat.Indx;
Jndx =mat.Jndx;
Rows =mat.Rows;
Cols =mat.Cols;
mat.nullify();
}
//=============================================================================
/*! resize the matrix */
inline void zgsmatrix::resize(const long& _m, const long& _n, const long _c)
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::resize(const long&, const long&, const long&)" << std::endl;
#endif//CPPL_VERBOSE
#ifdef CPPL_DEBUG
if( _m<0 || _n<0 || _c<0 ){
std::cerr << "[ERROR] zgsmatrix::resize(const long&, const long&, const long&)" << std::endl
<< "Matrix sizes and the length of arrays must be positive integers. " << std::endl
<< "Your input was (" << _m << "," << _n << "," << _c << ")." << std::endl;
exit(1);
}
#endif//CPPL_DEBUG
M =_m;
N =_n;
CAP =_c;
VOL =0;
delete [] Array;
Array =new std::complex<double>[CAP];
delete [] Indx;
Indx =new long[CAP];
delete [] Jndx;
Jndx =new long[CAP];
delete [] Rows;
Rows =new std::vector< std::pair<long,long> >[M];
delete [] Cols;
Cols =new std::vector< std::pair<long,long> >[N];
}
//=============================================================================
/*! stretch the matrix size */
inline void zgsmatrix::stretch(const long& dm, const long& dn)
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::stretch(const long&, const long&)" << std::endl;
#endif//CPPL_VERBOSE
#ifdef CPPL_DEBUG
if( m+dm<0 || n+dn<0 ){
std::cerr << "[ERROR] zgsmatrix::stretch(const long&, const long&)" << std::endl
<< "The new matrix size must be larger than zero. " << std::endl
<< "Your input was (" << dm << ", " << dn << ")." << std::endl;
exit(1);
}
#endif//CPPL_DEBUG
M +=dm;
N +=dn;
//// delete components over the new size ////
if(dm<0 || dn<0){
for(long c=VOL-1; c>=0; c--){
if(Indx[c]>=M || Jndx[c]>=N){ fdel(c); }
}
}
//// resize Rows and Cols ////
std::vector< std::pair<long,long> >* _Rows(new std::vector< std::pair<long,long> >[M]);
for(int i=0; i<min(M,M-dm); i++){ _Rows[i]=Rows[i]; }
delete [] Rows;
Rows=_Rows;
std::vector< std::pair<long,long> >* _Cols(new std::vector< std::pair<long,long> >[N]);
for(int i=0; i<min(N,N-dn); i++){ _Cols[i]=Cols[i]; }
delete [] Cols;
Cols=_Cols;
}
//=============================================================================
/*! expand the matrix capacity */
inline void zgsmatrix::expand(const long& dc)
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::expand(const long&)" << std::endl;
#endif//CPPL_VERBOSE
#ifdef CPPL_DEBUG
if( dc<0 ){
std::cerr << "[ERROR] zgsmatrix::expand(const long&)" << std::endl
<< "The argument must be a positive integer. " << std::endl
<< "Your input was (" << dc << ")." << std::endl;
exit(1);
}
#endif//CPPL_DEBUG
CAP+=dc;
std::complex<double>* newArray(new std::complex<double>[CAP]);
long *newIndx(new long[CAP]), *newJndx(new long[CAP]);
for(int c=0; c<VOL; c++){
newArray[c] =Array[c];
newIndx[c] =Indx[c];
newJndx[c] =Jndx[c];
}
delete [] Array;
delete [] Indx;
delete [] Jndx;
Array =newArray;
Indx =newIndx;
Jndx =newJndx;
}
//=============================================================================
/*! check if the component is listed */
inline bool zgsmatrix::isListed(const long& i, const long& j)
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::isListed(const long&, const long&)" << std::endl;
#endif//CPPL_VERBOSE
#ifdef CPPL_DEBUG
if( i<0 || j<0 || M<=i || N<=j ){
std::cerr << "[ERROR] zgsmatrix::isListed(const long&, const long&)"
<< std::endl
<< "The required component is out of the matrix size."
<< std::endl
<< "Your input was (" << i << "," << j << ")." << std::endl;
exit(1);
}
#endif//CPPL_DEBUG
for(std::vector< std::pair<long,long> >::iterator p=Rows[i].begin(); p!=Rows[i].end(); p++){
if(p->first==j){ return 1; }
}
return 0;
}
//=============================================================================
/*! return the element number of the component */
inline long zgsmatrix::number(const long& i, const long& j)
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::number(const long&, const long&)" << std::endl;
#endif//CPPL_VERBOSE
#ifdef CPPL_DEBUG
if( i<0 || j<0 || M<=i || N<=j ){
std::cerr << "[ERROR] zgsmatrix::number(const long&, const long&)" << std::endl
<< "The required component is out of the matrix size." << std::endl
<< "Your input was (" << i << "," << j << ")." << std::endl;
exit(1);
}
#endif//CPPL_DEBUG
for(std::vector< std::pair<long,long> >::iterator p=Rows[i].begin(); p!=Rows[i].end(); p++){
if(p->first==j){ return p->second; }
}
return -1;
}
//=============================================================================
/*! unique the component */
/*
inline void zgsmatrix::unique()
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::unique()" << std::endl;
#endif//CPPL_VERBOSE
for(long c=VOL-1; c>0; c--){
for(long d=c-1; d>=0; d--){
if(Indx[c]==Indx[d] && Jndx[c]==Jndx[d]){
Array[d]+=Array[c];
fdel(c);
}
}
}
}
*/
///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
//=============================================================================
/*! get row of the matrix */
inline _zrovector zgsmatrix::row(const long& _m) const
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::row(const long&)" << std::endl;
#endif//CPPL_VERBOSE
#ifdef CPPL_DEBUG
if( _m<0 || _m>M ){
std::cerr << "[ERROR] zgsmatrix::row(const long&)" << std::endl
<< "Input row number must be between 0 and " << M << "." << std::endl
<< "Your input was " << _m << "." << std::endl;
exit(1);
}
#endif//CPPL_DEBUG
zrovector v( zrovector(N).zero() );
for(std::vector< std::pair<long,long> >::const_iterator p=rows[_m].begin(); p!=rows[_m].end(); p++){
v(p->first)=Array[p->second];
}
return _(v);
}
//=============================================================================
/*! get column of the matrix */
inline _zcovector zgsmatrix::col(const long& _n) const
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::col(const long&)" << std::endl;
#endif//CPPL_VERBOSE
#ifdef CPPL_DEBUG
if( _n<0 || _n>N ){
std::cerr << "[ERROR] zgsmatrix::col(const long&)" << std::endl
<< "Input row number must be between 0 and " << N << "." << std::endl
<< "Your input was " << _n << "." << std::endl;
exit(1);
}
#endif//CPPL_DEBUG
zcovector v( zcovector(M).zero() );
for(std::vector< std::pair<long,long> >::const_iterator p=cols[_n].begin(); p!=cols[_n].end(); p++){
v(p->first)=Array[p->second];
}
return _(v);
}
///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
//=============================================================================
/*! swap two matrices */
inline void swap(zgsmatrix& A, zgsmatrix& B)
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] swap(zgsmatrix&, zgsmatrix&)" << std::endl;
#endif//CPPL_VERBOSE
long A_M(A.M), A_N(A.N), A_CAP(A.CAP), A_VOL(A.VOL);
std::complex<double>* A_Array(A.Array);
long *A_Indx(A.Indx), *A_Jndx(A.Jndx);
std::vector< std::pair<long,long> >* A_Rows(A.Rows), *A_Cols(A.Cols);
A.M=B.M; A.N=B.N; A.CAP=B.CAP; A.VOL=B.VOL;
A.Array=B.Array; A.Indx=B.Indx; A.Jndx=B.Jndx; A.Rows=B.Rows; A.Cols=B.Cols;
B.M=A_M; B.N=A_N; B.CAP=A_CAP; B.VOL=A_VOL;
B.Array=A_Array; B.Indx=A_Indx; B.Jndx=A_Jndx; B.Rows=A_Rows; B.Cols=A_Cols;
}
//=============================================================================
/*! convert user object to smart-temporary object */
inline _zgsmatrix _(zgsmatrix& mat)
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] _(zgsmatrix&)" << std::endl;
#endif//CPPL_VERBOSE
_zgsmatrix newmat;
newmat.M =mat.M;
newmat.N =mat.N;
newmat.CAP =mat.CAP;
newmat.VOL =mat.VOL;
newmat.Array =mat.Array;
newmat.Indx =mat.Indx;
newmat.Jndx =mat.Jndx;
newmat.Rows =mat.Rows;
newmat.Cols =mat.Cols;
mat.M =0;
mat.N =0;
mat.CAP =0;
mat.VOL =0;
mat.Array =NULL;
mat.Indx =NULL;
mat.Jndx =NULL;
mat.Rows =NULL;
mat.Cols =NULL;
return newmat;
}
///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
///////////////////////////////////////////////////////////////////////////////
//=============================================================================
/*! health checkup */
inline void zgsmatrix::checkup()
{
#ifdef CPPL_VERBOSE
std::cerr << "# [MARK] zgsmatrix::checkup()" << std::endl;
#endif//CPPL_VERBOSE
//////// write ////////
for(long c=0; c<VOL; c++){
std::cerr << "Array[" << c << "] = (" << Indx[c] << "," << Jndx[c] << ") = " << Array[c] << std::endl;
}
std::cerr << std::endl;
for(long i=0; i<M; i++){
std::cerr << "Rows[" << i << "] =" << std::flush;
for(unsigned long k=0; k<Rows[i].size(); k++){
std::cerr << " <" << Rows[i][k].first << "," << Rows[i][k].second << ">" << std::flush;
}
std::cerr << std::endl;
}
std::cerr << std::endl;
for(long j=0; j<N; j++){
std::cerr << "Cols[" << j << "] =" << std::flush;
for(unsigned long k=0; k<Cols[j].size(); k++){
std::cerr << " <" << Cols[j][k].first << "," << Cols[j][k].second << ">" << std::flush;
}
std::cerr << std::endl;
}
//////// CAP ////////
if(CAP<0){
std::cerr << "[ERROR] zgsmatrix::checkup()" << std::endl
<< "The cap is not valid." << std::endl
<< "CAP was " << CAP << "." << std::endl;
exit(1);
}
//////// VOL ////////
if(VOL<0 || VOL>CAP){
std::cerr << "[ERROR] zgsmatrix::checkup()" << std::endl
<< "The vol is not valid." << std::endl
<< "VOL was " << VOL << "while CAP is " << CAP << "."
<< std::endl;
exit(1);
}
//////// Elements ////////
for(long c=0; c<VOL; c++){
//// m bound ////
if(Indx[c]<0 || Indx[c]>=M){
std::cerr << "[ERROR] zgsmatrix::checkup()" << std::endl
<< "The indx of the " << c
<< "th element is out of the matrix size." << std::endl
<< "Indx[" << c << "] was " << Indx[c] << "." << std::endl;
exit(1);
}
//// n bound ////
if(Jndx[c]<0 || Jndx[c]>=N){
std::cerr << "[ERROR] zgsmatrix::checkup()" << std::endl
<< "The jndx of the " << c
<< "th element is out of the matrix size." << std::endl
<< "Jndx[" << c << "] was " << Jndx[c] << "." << std::endl;
exit(1);
}
//// std::complex<double>-listed ////
for(long C=c+1; C<VOL; C++){
if(Indx[c]==Indx[C] && Jndx[c]==Jndx[C]){
std::cerr << "[ERROR] zgsmatrix::checkup()" << std::endl
<< "The (" << Indx[c] << ", " << Jndx[c]
<< ") component is std::complex<double>-listed at the "
<< c << "th and the" << C << "the elements."<< std::endl;
exit(1);
}
}
}
//////// ijc consistence ////////
//////// NOTE ////////
std::cerr << "# [NOTE] zgsmatrix::checkup() "
<< "This sparse matrix is fine." << std::endl;
}