/* DFT++ is a density functional package developed by the research group of Professor Tomas Arias Copyright 1996-2003 Sohrab Ismail-Beigi This file is part of DFT++. DFT++ is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. DFT++ is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with DFT++; if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA Please see the file CREDITS for a list of authors. For academic users, we request that publications using results obtained with this software reference "New algebraic formulation of density functional calculation," by Sohrab Ismail-Beigi and T.A. Arias, Computer Physics Communications 128:1-2, 1-45 (June 2000). and, if using the wavelet basis, further reference "Multiresolution analysis of electronic structure: semicardinal and wavelet bases," T.A. Arias, Reviews of Modern Physics 71:1, 267-311 (January 1999). and "Robust ab initio calculation of condensed matter: transparent convergence through semicardinal multiresolution analysis,'' I.P. Daykov, T.A. Arias, and Torkel D. Engeness, Physical Review Letters, 90:21, 216402 (May 2003). For your convenience, preprints of the above articles may be obtained from http://arXiv.org/abs/cond-mat/9909130, 9805262, and 0204411, respectively. */ /* * Sohrab Ismail-Beigi, Dec. 1996 * * A simple complex number class for C++. I tried to make it as efficient * as possible. * */ /* $Id: complex.h,v 1.7.2.5 2003/05/29 18:54:15 ivan Exp $ */ #ifndef DFT_COMPLEX_H #define DFT_COMPLEX_H #include #include class complex { // data public: real x,y; complex(real r = 0, real i = 0): x(r), y(i) {} complex& operator += (const complex&); complex& operator -= (const complex&); complex& operator *= (const complex&); // operators inline void operator=(const real x1) { x = x1; y = (real)0.0; } inline void operator*=(const real s) // z *= r { x *= s; y *= s; } // functions inline real phase() const { return atan2(y,x); } }; // Returns the complex conjugate of z inline complex conj(const complex& z) { return complex( z.x, -z.y ); } inline complex& complex::operator += (const complex& r) { x+=r.x; y+=r.y; return *this; } inline complex& complex::operator -= (const complex& r) { x-=r.x; y-=r.y; return *this; } inline complex& complex::operator *= (const complex& r) { real f = x*r.x - y*r.y; y = x*r.y + y*r.x; x = f; return *this; } inline complex operator + (const complex& z) { return z; } inline complex operator - (const complex& z) { return complex(-z.x, -z.y); } inline complex operator + (const complex& z1, const complex& z2) { return complex(z1.x+z2.x, z1.y + z2.y); } inline complex operator - (const complex& z1, const complex& z2) { return complex(z1.x-z2.x, z1.y - z2.y); } inline complex operator * (const complex& z1, const complex& z2) { return complex(z1.x * z2.x - z1.y * z2.y, z1.x * z2.y + z1.y * z2.x); } inline complex operator / (const complex& z1, const complex& z2) { real s=(real)1.0/(z2.x*z2.x+z2.y*z2.y); return complex( s*(z1.x*z2.x+z1.y*z2.y), s*(z1.y*z2.x-z1.x*z2.y) ); } inline complex operator * (const complex& z, real r) { return complex(z.x * r, z.y * r); } inline complex operator * (real r, const complex& z) { return complex(r * z.x, r * z.y); } inline complex operator / (const complex& z, real r) { return complex(z.x / r, z.y / r); } // friend operator/ overload to handle real/complex case inline complex operator/(const real s,const complex &z1) { real soverz2 = s/(z1.x*z1.x+z1.y*z1.y); return complex(soverz2*z1.x, -soverz2*z1.y); } // Returns square magnitude of z inline real abs2(const complex &z) { return z.x*z.x + z.y*z.y; } // Returns length of z inline real abs(const complex &z) { return sqrt(z.x*z.x+z.y*z.y); } // Returns phase of z from -pi to pi inline real phase(const complex &z) { return atan2(z.y,z.x); } // Exponentiates z inline complex exp(const complex &z) { real s = exp(z.x); return complex( s*cos(z.y), s*sin(z.y) ); } // Returns the natural log of z with phase from -pi to pi inline complex ln(const complex &z) { return complex( 0.5*log(abs2(z)), z.phase() ); } // Returns sqrt of z with phase of z taken from -pi to pi inline complex sqrt(const complex &z) { real r = sqrt(abs(z)); real theta = 0.5*z.phase(); return complex( r*cos(theta), r*sin(theta) ); } inline real REAL(const complex &z) {return z.x;} inline real IMAG(const complex &z) {return z.y;} #endif // DFT_COMPLEX_H