Hauptseite | Liste aller Namensbereiche | Klassenhierarchie | Auflistung der Klassen | Auflistung der Dateien | Elemente eines Namensbereiches | Klassen-Elemente | Datei-Elemente

SHRotateMatrix.h

gehe zur Dokumentation dieser Datei
00001 00002 00003 00004 00005 00006 00007 00008 00009 00010 00011 00012 00013 #ifndef _ZFXMATH_INCLUDE_SH_ROTATEMATRIX_H_ 00014 #define _ZFXMATH_INCLUDE_SH_ROTATEMATRIX_H_ 00015 00016 namespace ZFXMath 00017 { 00018 00019 namespace SphericalHarmonics 00020 { 00021 00027 template<class PrecisionType, class FuncValueType> 00028 class TRotateMatrix 00029 { 00030 public: 00031 TRotateMatrix(const int nb_bands) : 00032 00033 m_NbBands(nb_bands), 00034 m_Matrices(0), 00035 m_Elements(0) 00036 00037 { 00039 m_Matrices = (SubMatrix*)operator new (m_NbBands * sizeof(SubMatrix)); 00040 00041 int size = 0; 00042 for (int i = 0; i < m_NbBands; i++) 00043 size += (i * 2 + 1) * (i * 2 + 1); 00044 00046 m_Elements = new PrecisionType[size]; 00047 00049 for (int i = 0, j = 0; i < m_NbBands; i++) 00050 { 00051 int w = i * 2 + 1; 00052 m_Matrices[i] = *new SubMatrix(m_Elements + j, w); 00053 j += (w * w); 00054 } 00055 00056 // The first 1x1 sub-matrix is always 1 and so doesn't need to be stored in the rotation matrix 00057 // It's stored simply to make the indexing logic as easy as possible 00058 m_Elements[0] = 1; 00059 } 00060 00061 00062 ~TRotateMatrix(void) 00063 { 00064 if (m_Elements) 00065 delete [] m_Elements; 00066 if (m_Matrices) 00067 delete [] m_Matrices; 00068 } 00069 00070 00071 // Element accessors which take the band index and (+,-) index relative to the centre of the sub-matrix 00072 PrecisionType& operator () (const int l, const int m, const int n) 00073 { 00074 return (m_Matrices[l](m, n)); 00075 } 00076 PrecisionType operator () (const int l, const int m, const int n) const 00077 { 00078 return (m_Matrices[l](m, n)); 00079 } 00080 00081 00082 int GetNbBands(void) const 00083 { 00084 return (m_NbBands); 00085 } 00086 00092 void Transform(const TCoeffs<FuncValueType>& source, TCoeffs<FuncValueType>& dest) const 00093 { 00094 // Check number of bands match 00095 int nb_bands = source.GetNbBands(); 00096 assert(nb_bands == dest.GetNbBands()); 00097 00098 // Band 0 is always multiplied by 1 so it stays untouched 00099 dest(0) = source(0); 00100 00101 // Loop through each band 00102 for (int l = 1; l < nb_bands; l++) 00103 { 00104 SubMatrix& M = m_Matrices[l]; 00105 00106 // Calculate band offset into coeff list 00107 int band_offset = l * (l + 1); 00108 00109 // Now through each argument of the destination coeff-list 00110 for (int mo = -l; mo <= l; mo++) 00111 { 00112 // Clear destination 00113 FuncValueType& d = dest(band_offset + mo); 00114 d = 0; 00115 00116 // Pre-calculate of mo's lookup in the sub-matrix, plus mi's shift 00117 int p_mo = (mo + M.GetShift()) * M.GetWidth() + M.GetShift(); 00118 00119 // Multiply-add with each argument of the source coeff-list 00120 for (int mi = -l; mi <= l; mi++) 00121 d += source(band_offset + mi) * FuncValueType( M(p_mo + mi) ); 00122 } 00123 } 00124 } 00125 00126 private: 00127 class SubMatrix; 00128 00129 // Number of bands stored 00130 int m_NbBands; 00131 00132 // Sub-matrix for each band 00133 SubMatrix* m_Matrices; 00134 00135 // Element array for each sub-matrix 00136 PrecisionType* m_Elements; 00137 00138 class SubMatrix 00139 { 00140 public: 00141 // Construct that needs previously allocated element array 00142 SubMatrix(PrecisionType* elements, const int width) : 00143 00144 m_Elements(elements), 00145 m_Width(width), 00146 m_Size(width * width), 00147 m_Shift((width - 1) / 2) 00148 00149 { 00150 } 00151 00152 00153 // Element accessors with (+,-) lookup 00154 PrecisionType& operator () (const int m, const int n) 00155 { 00156 return (m_Elements[Index(m, n)]); 00157 } 00158 PrecisionType operator () (const int m, const int n) const 00159 { 00160 return (m_Elements[Index(m, n)]); 00161 } 00162 00163 00164 // Linear element accessors 00165 PrecisionType& operator () (const int i) 00166 { 00167 return (m_Elements[Index(i)]); 00168 } 00169 PrecisionType operator () (const int i) const 00170 { 00171 return (m_Elements[Index(i)]); 00172 } 00173 00174 00175 int GetWidth(void) const 00176 { 00177 return (m_Width); 00178 } 00179 00180 int GetShift(void) const 00181 { 00182 return (m_Shift); 00183 } 00184 00185 00186 private: 00187 00188 int Index(const int m, const int n) const 00189 { 00190 // Check bounds in debug build 00191 assert(m >= -m_Shift && m <= m_Shift); 00192 assert(n >= -m_Shift && n <= m_Shift); 00193 00194 return ((m + m_Shift) * m_Width + (n + m_Shift)); 00195 } 00196 00197 int Index(const int i) const 00198 { 00199 // Check bounds in debug build 00200 assert(i >= 0 && i < m_Size); 00201 00202 return (i); 00203 } 00204 00205 // Element array 00206 PrecisionType* m_Elements; 00207 00208 // Width of the sub-matrix 00209 int m_Width; 00210 00211 // Total size of the sub-matrix in multiples of PrecisionType 00212 int m_Size; 00213 00214 // Value to shift incoming matrix indices by 00215 int m_Shift; 00216 }; 00217 00218 }; // class TRotateMatrix 00219 00220 }; // namespace SphericalHarmonics 00221 00222 }; // namespace ZFXMath 00223 00224 #endif //_ZFXMATH_INCLUDE_SH_ROTATEMATRIX_H__

Erzeugt am Thu Nov 25 04:02:55 2004 für ZFX-Math Library von doxygen 1.3.8