Tensor.h

Go to the documentation of this file.
00001 
00007 #ifndef TENSOR_H
00008 #define TENSOR_H
00009 
00010 #include <math.h>
00011 #include <stdio.h>
00012 #include "common.h"
00013 #include "Vector.h"
00014 
00015 class Tensor {
00016    public:
00017      BigReal xx, xy, xz;
00018      BigReal yx, yy, yz;
00019      BigReal zx, zy, zz;
00020      
00021      inline Tensor(void) {
00022        xx=xy=xz=yx=yy=yz=zx=zy=zz=0.0;
00023      }
00024 
00025      inline Tensor(const Tensor &t2) {
00026        xx = t2.xx; xy = t2.xy; xz = t2.xz;
00027        yx = t2.yx; yy = t2.yy; yz = t2.yz;
00028        zx = t2.zx; zy = t2.zy; zz = t2.zz;
00029      }
00030 
00031      static inline Tensor identity(BigReal v1 = 1.0) {
00032        Tensor tmp;
00033        tmp.xx = tmp.yy = tmp.zz = v1;
00034        return tmp;
00035      }
00036 
00037      static inline Tensor diagonal(const Vector &v1) {
00038        Tensor tmp;
00039        tmp.xx = v1.x; tmp.xy = 0; tmp.xz = 0;
00040        tmp.yx = 0; tmp.yy = v1.y; tmp.yz = 0;
00041        tmp.zx = 0; tmp.zy = 0; tmp.zz = v1.z;
00042        return tmp;
00043      }
00044 
00045      static inline Tensor symmetric(const Vector &v1, const Vector &v2) {
00046        Tensor tmp;
00047        tmp.xx = v1.x; tmp.xy = v2.x; tmp.xz = v2.y;
00048        tmp.yx = v2.x; tmp.yy = v1.y; tmp.yz = v2.z;
00049        tmp.zx = v2.y; tmp.zy = v2.z; tmp.zz = v1.z;
00050        return tmp;
00051      }
00052 
00053      static inline Tensor triangular(const Vector &v1, const Vector &v2) {
00054        Tensor tmp;
00055        tmp.xx = v1.x; tmp.xy = v2.x; tmp.xz = v2.y;
00056        tmp.yx = 0; tmp.yy = v1.y; tmp.yz = v2.z;
00057        tmp.zx = 0; tmp.zy = 0; tmp.zz = v1.z;
00058        return tmp;
00059      }
00060 
00061      ~Tensor(void) { }
00062 
00063      inline Tensor& operator=(const Tensor &t2) {
00064        xx = t2.xx; xy = t2.xy; xz = t2.xz;
00065        yx = t2.yx; yy = t2.yy; yz = t2.yz;
00066        zx = t2.zx; zy = t2.zy; zz = t2.zz;
00067        return *this;
00068      }
00069 
00070      inline Tensor& operator=(const BigReal &r2) {
00071        xx=xy=xz=yx=yy=yz=zx=zy=zz=r2;
00072        return *this;
00073      }
00074 
00075      inline Tensor& operator+=(const Tensor &t2) {
00076        xx += t2.xx; xy += t2.xy; xz += t2.xz;
00077        yx += t2.yx; yy += t2.yy; yz += t2.yz;
00078        zx += t2.zx; zy += t2.zy; zz += t2.zz;
00079        return *this;
00080      }
00081 
00082      inline Tensor& operator-=(const Tensor &t2) {
00083        xx -= t2.xx; xy -= t2.xy; xz -= t2.xz;
00084        yx -= t2.yx; yy -= t2.yy; yz -= t2.yz;
00085        zx -= t2.zx; zy -= t2.zy; zz -= t2.zz;
00086        return *this;
00087      }
00088 
00089      inline Tensor& operator*=(const BigReal &r2) {
00090        xx *= r2; xy *= r2; xz *= r2;
00091        yx *= r2; yy *= r2; yz *= r2;
00092        zx *= r2; zy *= r2; zz *= r2;
00093        return *this;
00094      }
00095 
00096      inline Tensor& operator/=(const BigReal &r2) {
00097        xx /= r2; xy /= r2; xz /= r2;
00098        yx /= r2; yy /= r2; yz /= r2;
00099        zx /= r2; zy /= r2; zz /= r2;
00100        return *this;
00101      }
00102 
00103      inline void outerAdd (BigReal scale, const Vector &v1, const Vector &v2);
00104 
00105      inline friend int operator==(const Tensor &t1, const Tensor &t2) {
00106        return (
00107        t1.xx == t2.xx && t1.xy == t2.xy && t1.xz == t2.xz &&
00108        t1.yx == t2.yx && t1.yy == t2.yy && t1.yz == t2.yz &&
00109        t1.zx == t2.zx && t1.zy == t2.zy && t1.zz == t2.zz );
00110      }
00111 
00112      inline friend int operator!=(const Tensor &t1, const Tensor &t2) {
00113        return ( ! ( t1 == t2 ) );
00114      }
00115 
00116      inline friend Tensor operator+(const Tensor& t1, const Tensor& t2) {
00117        Tensor tmp(t1);
00118        tmp += t2;
00119        return tmp;
00120      }
00121 
00122      inline friend Tensor operator-(const Tensor& t1, const Tensor& t2) {
00123        Tensor tmp(t1);
00124        tmp -= t2;
00125        return tmp;
00126      }
00127 
00128      inline friend Tensor operator-(const Tensor &t1) {
00129        Tensor tmp(t1);
00130        tmp *= -1.0;
00131        return tmp;
00132      }
00133 
00134      inline friend Tensor operator*(const BigReal &r1, const Tensor &t2) {
00135        Tensor tmp(t2);
00136        tmp *= r1;
00137        return tmp;
00138      }
00139 
00140      inline friend Tensor operator*(const Tensor &t1, const BigReal &r2) {
00141        Tensor tmp(t1);
00142        tmp *= r2;
00143        return tmp;
00144      }
00145 
00146      inline friend Tensor operator/(const Tensor &t1, const BigReal &r2) {
00147        Tensor tmp(t1);
00148        tmp /= r2;
00149        return tmp;
00150      }
00151 
00152      inline friend Vector operator*(const Tensor &t1, const Vector &v2) {
00153        Vector tmp;
00154        tmp.x = t1.xx * v2.x + t1.xy * v2.y + t1.xz * v2.z;
00155        tmp.y = t1.yx * v2.x + t1.yy * v2.y + t1.yz * v2.z;
00156        tmp.z = t1.zx * v2.x + t1.zy * v2.y + t1.zz * v2.z;
00157        return tmp;
00158      }
00159 
00160      inline friend Vector operator*(const Vector &v1, const Tensor &t2) {
00161        Vector tmp;
00162        tmp.x = t2.xx * v1.x + t2.yx * v1.y + t2.zx * v1.z;
00163        tmp.y = t2.xy * v1.x + t2.yy * v1.y + t2.zy * v1.z;
00164        tmp.z = t2.xz * v1.x + t2.yz * v1.y + t2.zz * v1.z;
00165        return tmp;
00166      }
00167 
00168      inline friend Tensor outer(const Vector &v1, const Vector &v2);
00169 
00170      inline friend Tensor transpose(const Tensor &t1) {
00171        Tensor tmp;
00172        tmp.xx = t1.xx; tmp.yx = t1.xy; tmp.zx = t1.xz;
00173        tmp.xy = t1.yx; tmp.yy = t1.yy; tmp.zy = t1.yz;
00174        tmp.xz = t1.zx; tmp.yz = t1.zy; tmp.zz = t1.zz;
00175        return tmp;
00176      }
00177 
00178      inline friend Tensor symmetric(const Tensor &t1) {
00179        Tensor tmp;
00180        tmp.xx = t1.xx; tmp.xy = 0.5*(t1.xy+t1.yx); tmp.xz = 0.5*(t1.xz+t1.zx);
00181        tmp.yx = tmp.xy; tmp.yy = t1.yy; tmp.yz = 0.5*(t1.yz+t1.zy);
00182        tmp.zx = tmp.xz; tmp.zy = tmp.yz; tmp.zz = t1.zz;
00183        return tmp;
00184      }
00185 
00186      inline friend Tensor triangular(const Tensor &t1) {
00187        Tensor tmp;
00188        tmp.xx = t1.xx; tmp.xy = 0.5*(t1.xy+t1.yx); tmp.xz = 0.5*(t1.xz+t1.zx);
00189        tmp.yx = 0; tmp.yy = t1.yy; tmp.yz = 0.5*(t1.yz+t1.zy);
00190        tmp.zx = 0; tmp.zy = 0; tmp.zz = t1.zz;
00191        return tmp;
00192      }
00193 
00194      inline friend Vector diagonal(const Tensor &t1) {
00195        return Vector(t1.xx,t1.yy,t1.zz);
00196      }
00197 
00198      inline friend Vector off_diagonal(const Tensor &t1) {
00199        return Vector(t1.xy,t1.xz,t1.yz);
00200      }
00201 
00202      inline friend BigReal trace(const Tensor &t1) {
00203        return (t1.xx + t1.yy + t1.zz);
00204      }
00205 
00206 /*
00207      // set the vector based on a string.  If bad, return FALSE
00208      // the string can be in the form "x y z" or "x, y, z"
00209      Bool set(const char *s) {
00210         double a[3];    // read into doubles, since I don't know what
00211         char tmp[100];  // a "BigReal" is in real life
00212         // cheap way to get commas, etc.  a poor regex
00213        int i=sscanf(s, "%lf%99[ \t,]%lf%99[ \t,]%lf%99s",
00214                     a, tmp, a+1, tmp, a+2, tmp);
00215        if (i != 5) return FALSE;
00216        const char *t = s;       // now count commas (for "1,,,,2,  , 3")
00217        int flg = 0;                 // and check for "1 2,,3"
00218        i = 0;
00219        for (;*t;t++) {
00220           if (*t == ',') { 
00221              if (flg == 0) {   // expecting non-whitespace
00222                 return FALSE;  //    so error
00223              }
00224              flg = 0;          // now expect non-whitespace
00225              i++;              // and increment comma counter
00226           }
00227           else if (*t != ' ' && *t != '\t') {  // got non-whitespace
00228              flg = 1;          // so the next can be whitespace or commas
00229           }
00230        }
00231        if (i == 0 || i == 2) {  // allow "1 2 3" or "1, 2,3" forms
00232           x = a[0]; y = a[1]; z = a[2];
00233           return TRUE;
00234        }
00235        return FALSE;
00236      }
00237 */
00238 
00239 };
00240 
00241 inline Tensor outer(const Vector &v1, const Vector &v2) {
00242        Tensor tmp;
00243        tmp.xx = v1.x * v2.x;
00244        tmp.xy = v1.x * v2.y;
00245        tmp.xz = v1.x * v2.z;
00246        tmp.yx = v1.y * v2.x;
00247        tmp.yy = v1.y * v2.y;
00248        tmp.yz = v1.y * v2.z;
00249        tmp.zx = v1.z * v2.x;
00250        tmp.zy = v1.z * v2.y;
00251        tmp.zz = v1.z * v2.z;
00252        return tmp;
00253 }
00254 
00255 inline void Tensor::outerAdd (BigReal scale, const Vector &v1, const Vector &v2) {
00256   xx += v1.x * v2.x * scale;
00257   xy += v1.x * v2.y * scale;
00258   xz += v1.x * v2.z * scale;
00259   yx += v1.y * v2.x * scale;
00260   yy += v1.y * v2.y * scale;
00261   yz += v1.y * v2.z * scale;
00262   zx += v1.z * v2.x * scale;
00263   zy += v1.z * v2.y * scale;
00264   zz += v1.z * v2.z * scale;
00265 }
00266 
00267 #endif
00268 

Generated on Mon Nov 20 01:17:15 2017 for NAMD by  doxygen 1.4.7