source: Sophya/trunk/SophyaLib/TArray/tmatrix.cc@ 1096

Last change on this file since 1096 was 1081, checked in by ansari, 25 years ago

Adaptation modifs MuTyV et services de copie entre tableaux de type different - Reza 24/7/2000

File size: 10.4 KB
RevLine 
[1081]1// $Id: tmatrix.cc,v 1.13 2000-07-24 12:51:27 ansari Exp $
[762]2// C.Magneville 04/99
3#include "machdefs.h"
4#include <stdio.h>
5#include <stdlib.h>
6#include "pexceptions.h"
7#include "tmatrix.h"
8
[926]9/*!
10 \class SOPHYA::TMatrix
11 \ingroup TArray
12 Class of matrixes
13 \sa TArray
14 */
[804]15
[762]16////////////////////////////////////////////////////////////////
17//**** Createur, Destructeur
[894]18//! Default constructor
[762]19template <class T>
20TMatrix<T>::TMatrix()
21// Constructeur par defaut.
[804]22 : TArray<T>()
[762]23{
[813]24 ck_memo_vt_ = true;
[762]25}
26
[894]27//! constructor of a matrix with r lines et c columns.
28/*!
29 \param r : number of rows
30 \param c : number of columns
31 \param mm : define the memory mapping type
32 \sa ReSize
33 */
[762]34template <class T>
[804]35TMatrix<T>::TMatrix(uint_4 r,uint_4 c, short mm)
[762]36// Construit une matrice de r lignes et c colonnes.
[804]37 : TArray<T>()
[762]38{
[804]39 if ( (r == 0) || (c == 0) )
40 throw ParmError("TMatrix<T>::TMatrix(uint_4 r,uint_4 c) NRows or NCols = 0");
41 ReSize(r, c, mm);
[762]42}
43
[967]44//! Constructor by copy
[976]45/*!
46 \warning datas are \b SHARED with \b a.
47 \sa NDataBlock::NDataBlock(const NDataBlock<T>&)
48*/
[762]49template <class T>
50TMatrix<T>::TMatrix(const TMatrix<T>& a)
[967]51// Constructeur par copie
[804]52 : TArray<T>(a)
[762]53{
54}
55
[894]56//! Constructor by copy
57/*!
58 \param share : if true, share data. If false copy data
59 */
[762]60template <class T>
[804]61TMatrix<T>::TMatrix(const TMatrix<T>& a, bool share)
[762]62// Constructeur par copie avec possibilite de forcer le partage ou non.
[804]63: TArray<T>(a, share)
[762]64{
65}
66
[894]67//! Constructor of a matrix from a TArray \b a
[762]68template <class T>
[804]69TMatrix<T>::TMatrix(const TArray<T>& a)
70: TArray<T>(a)
[762]71{
[813]72 if (a.NbDimensions() > 2)
73 throw SzMismatchError("TMatrix<T>::TMatrix(const TArray<T>& a) a.NbDimensions()>2 ");
74 if (a.NbDimensions() == 1) {
75 size_[1] = 1;
76 step_[1] = size_[0]*step_[0];
77 ndim_ = 2;
78 }
79 UpdateMemoryMapping(a, SameMemoryMapping);
[762]80}
81
[894]82//! Constructor of a matrix from a TArray \b a
83/*!
84 \param a : TArray to be copied or shared
85 \param share : if true, share data. If false copy data
86 \param mm : define the memory mapping type
87 */
[762]88template <class T>
[804]89TMatrix<T>::TMatrix(const TArray<T>& a, bool share, short mm )
90: TArray<T>(a, share)
[762]91{
[813]92 if (a.NbDimensions() > 2)
93 throw SzMismatchError("TMatrix<T>::TMatrix(const TArray<T>& a, ...) a.NbDimensions()>2");
94 if (a.NbDimensions() == 1) {
95 size_[1] = 1;
96 step_[1] = size_[0]*step_[0];
97 ndim_ = 2;
98 }
[804]99 UpdateMemoryMapping(a, mm);
[762]100}
101
[1081]102template <class T>
103TMatrix<T>::TMatrix(const BaseArray& a)
104: TArray<T>()
105{
106 SetBA(a);
107}
108
109
110
[894]111//! Destructor
[762]112template <class T>
[804]113TMatrix<T>::~TMatrix()
[762]114{
115}
116
[976]117//! Set matrix equal to \b a and return *this
118/*!
119 \warning Datas are copied (cloned) from \b a.
120 \sa NDataBlock::operator=(const NDataBlock<T>&)
121*/
[804]122template <class T>
123TArray<T>& TMatrix<T>::Set(const TArray<T>& a)
[762]124{
[813]125 if (a.NbDimensions() > 2)
126 throw SzMismatchError("TMatrix<T>::Set(const TArray<T>& a) a.NbDimensions() > 2");
127 TArray<T>::Set(a);
[970]128 if (NbDimensions() == 1) {
[813]129 size_[1] = 1;
130 step_[1] = size_[0]*step_[0];
131 ndim_ = 2;
132 }
[970]133 UpdateMemoryMapping(*this, SameMemoryMapping);
[813]134 return(*this);
[762]135}
136
[1081]137template <class T>
138TArray<T>& TMatrix<T>::SetBA(const BaseArray& a)
139{
140 if (a.NbDimensions() > 2)
141 throw SzMismatchError("TMatrix<T>::SetBA(const BaseArray& a) a.NbDimensions() > 2");
142 TArray<T>::SetBA(a);
143 if (NbDimensions() == 1) {
144 size_[1] = 1;
145 step_[1] = size_[0]*step_[0];
146 ndim_ = 2;
147 }
148 UpdateMemoryMapping(*this, SameMemoryMapping);
149 return(*this);
150}
151
152
153
[894]154//! Resize the matrix
155/*!
156 \param r : number of rows
157 \param c : number of columns
158 \param mm : define the memory mapping type
159 (SameMemoryMapping,CMemoryMapping
160 ,FortranMemoryMapping,DefaultMemoryMapping)
161 */
[804]162template <class T>
163void TMatrix<T>::ReSize(uint_4 r, uint_4 c, short mm)
[762]164{
[804]165 if(r==0||c==0)
166 throw(SzMismatchError("TMatrix::ReSize r or c==0 "));
167 uint_4 size[BASEARRAY_MAXNDIMS];
168 for(int kk=0; kk<BASEARRAY_MAXNDIMS; kk++) size[kk] = 0;
169 if (mm == SameMemoryMapping) mm = GetMemoryMapping();
[813]170 else if ( (mm != CMemoryMapping) && (mm != FortranMemoryMapping) )
171 mm = GetDefaultMemoryMapping();
172 if (mm == CMemoryMapping) {
173 size[0] = c; size[1] = r;
174 }
175 else {
176 size[0] = r; size[1] = c;
177 }
[804]178 TArray<T>::ReSize(2, size, 1);
[813]179 UpdateMemoryMapping(mm);
[762]180}
181
[894]182//! Re-allocate space for the matrix
183/*!
184 \param r : number of rows
185 \param c : number of columns
186 \param mm : define the memory mapping type
187 \param force : if true re-allocation is forced, if not it occurs
188 only if the required space is greater than the old one.
189 \sa ReSize
190 */
[762]191template <class T>
[804]192void TMatrix<T>::Realloc(uint_4 r,uint_4 c, short mm, bool force)
[762]193{
[804]194 if(r==0||c==0)
195 throw(SzMismatchError("TMatrix::Realloc r or c==0 "));
196 uint_4 size[BASEARRAY_MAXNDIMS];
197 for(int kk=0; kk<BASEARRAY_MAXNDIMS; kk++) size[kk] = 0;
[813]198 if (mm == SameMemoryMapping) mm = GetMemoryMapping();
199 else if ( (mm != CMemoryMapping) && (mm != FortranMemoryMapping) )
200 mm = GetDefaultMemoryMapping();
201 if (mm == CMemoryMapping) {
202 size[0] = c; size[1] = r;
203 }
204 else {
205 size[0] = r; size[1] = c;
206 }
[804]207 TArray<T>::Realloc(2, size, 1, force);
[813]208 UpdateMemoryMapping(mm);
[762]209}
210
[804]211// $CHECK$ Reza 03/2000 Doit-on declarer cette methode const ?
[894]212//! Return a submatrix define by \b Range \b rline and \b rcol
[762]213template <class T>
[813]214TMatrix<T> TMatrix<T>::SubMatrix(Range rline, Range rcol) const
[762]215{
[813]216 short mm = GetMemoryMapping();
217 Range rx, ry;
218 if (mm == CMemoryMapping) { rx = rcol; ry = rline; }
219 else { ry = rcol; rx = rline; }
220 TMatrix sm(SubArray(rx, ry, Range(0), Range(0), Range(0)),true, mm);
221 sm.UpdateMemoryMapping(mm);
222 sm.SetTemp(true);
223 return(sm);
[762]224}
225
[804]226////////////////////////////////////////////////////////////////
227// Transposition
[894]228//! Transpose matrix in place
[762]229template <class T>
[804]230TMatrix<T>& TMatrix<T>::Transpose()
231{
[813]232 short vt = (marowi_ == veceli_) ? ColumnVector : RowVector;
[804]233 uint_4 rci = macoli_;
234 macoli_ = marowi_;
235 marowi_ = rci;
[813]236 veceli_ = (vt == ColumnVector ) ? marowi_ : macoli_;
[804]237 return(*this);
[762]238}
239
240
[894]241//! Transpose matrix into new matrix
242/*!
243 \param mm : define the memory mapping type
244 (SameMemoryMapping,CMemoryMapping,FortranMemoryMapping)
245 \return return a new matrix
246 */
[762]247template <class T>
[804]248TMatrix<T> TMatrix<T>::Transpose(short mm)
[762]249{
[804]250 if (mm == SameMemoryMapping) mm = GetMemoryMapping();
251 TMatrix<T> tm(NCols(), NRows(), mm);
252 for(uint_4 i=0; i<NRows(); i++)
253 for(uint_4 j=0; j<NCols(); j++)
254 tm(j,i) = (*this)(i,j);
255 tm.SetTemp(true);
256 return tm;
[762]257}
258
[894]259//! Rearrange data in memory memoire according to \b mm
260/*!
261 \param mm : define the memory mapping type
262 (SameMemoryMapping,CMemoryMapping,FortranMemoryMapping)
263 \warning If identical, return a matrix that share the datas
264 */
[762]265template <class T>
[804]266TMatrix<T> TMatrix<T>::Rearrange(short mm)
[762]267{
[813]268 if ( mm == SameMemoryMapping) mm = GetMemoryMapping();
269 else if ( (mm != CMemoryMapping) && (mm != FortranMemoryMapping) )
270 mm = GetDefaultMemoryMapping();
271
272 if (mm == GetMemoryMapping())
273 return (TMatrix<T>(*this, true));
274
[804]275 TMatrix<T> tm(NRows(), NCols(), mm);
276 for(uint_4 i=0; i<NRows(); i++)
277 for(uint_4 j=0; j<NCols(); j++)
278 tm(i,j) = (*this)(i,j);
279 tm.SetTemp(true);
280 return tm;
[762]281}
282
[894]283//! Set the matrix to the identity matrix \b imx
[762]284template <class T>
[804]285TMatrix<T>& TMatrix<T>::SetIdentity(IdentityMatrix imx)
[762]286{
[804]287 if (ndim_ == 0) {
288 uint_4 sz = imx.Size();
289 if (sz < 1) sz = 1;
290 ReSize(sz, sz);
291 }
292 T diag = (T)imx.Diag();
293 if (NRows() != NCols())
294 throw SzMismatchError("TMatrix::operator= (IdentityMatrix) NRows() != NCols()") ;
[996]295 *this = (T) 0;
[804]296 for(uint_4 i=0; i<NRows(); i++) (*this)(i,i) = diag;
[762]297
[804]298 return (*this);
[762]299}
300
[804]301
302
303////////////////////////////////////////////////////////////////
304//**** Impression
[894]305//! Return info on number of rows, column and type \b T
[762]306template <class T>
[813]307string TMatrix<T>::InfoString() const
308{
309 string rs = "TMatrix<";
310 rs += typeid(T).name();
311 char buff[64];
312 sprintf(buff, ">(NRows=%ld, NCols=%ld)", (long)NRows(), (long)NCols());
313 rs += buff;
314 return(rs);
315}
316
[894]317//! Print matrix
318/*!
319 \param maxprt : maximum numer of print
320 \param si : if true, display attached DvList
321 \sa SetMaxPrint
322 */
[813]323template <class T>
[804]324void TMatrix<T>::Print(ostream& os, int_4 maxprt, bool si) const
[762]325{
[804]326 if (maxprt < 0) maxprt = max_nprt_;
[958]327 uint_4 npr = 0;
[804]328 Show(os, si);
[850]329 if (ndim_ < 1) return;
[804]330 uint_4 kc,kr;
331 for(kr=0; kr<size_[marowi_]; kr++) {
332 if ( (size_[marowi_] > 1) && (size_[macoli_] > 10) ) cout << "----- Ligne Line= " << kr << endl;
333 for(kc=0; kc<size_[macoli_]; kc++) {
334 if(kc > 0) os << ", ";
335 os << (*this)(kr, kc); npr++;
[958]336 if (npr >= (uint_4) maxprt) {
[804]337 if (npr < totsize_) os << "\n .... " << endl; return;
338 }
339 }
340 os << endl;
341 }
[813]342 os << endl;
[762]343}
344
345////////////////////////////////////////////////////////////////
[804]346//**** Multiplication matricielle *****
[762]347////////////////////////////////////////////////////////////////
348
[894]349//! Return the matrix product C = (*this)*B
350/*!
351 \param mm : define the memory mapping type for the return matrix
352 */
[804]353template <class T>
354TMatrix<T> TMatrix<T>::Multiply(const TMatrix<T>& b, short mm) const
355{
356 if (NCols() != b.NRows())
357 throw(SzMismatchError("TMatrix<T>::Multiply(b) NCols() != b.NRows() ") );
358 if (mm == SameMemoryMapping) mm = GetMemoryMapping();
359 TMatrix<T> rm(NRows(), b.NCols(), mm);
[762]360
[804]361 const T * pea;
362 const T * peb;
363 T sum;
364 uint_4 r,c,k;
365 uint_4 stepa = Step(ColsKA());
366 uint_4 stepb = b.Step(RowsKA());
367 // Calcul de C=rm = A*B (A=*this)
368 for(r=0; r<rm.NRows(); r++) // Boucle sur les lignes de A
369 for(c=0; c<rm.NCols(); c++) { // Boucle sur les colonnes de B
370 sum = 0;
371 pea = &((*this)(r,0)); // 1er element de la ligne r de A
372 peb = &(b(0,c)); // 1er element de la colonne c de B
373 for(k=0; k<NCols(); k++) sum += pea[k*stepa]*peb[k*stepb];
374 rm(r,c) = sum;
375 }
376
377 rm.SetTemp(true);
378 return rm;
379}
380
[762]381///////////////////////////////////////////////////////////////
382#ifdef __CXX_PRAGMA_TEMPLATES__
383#pragma define_template TMatrix<uint_2>
384#pragma define_template TMatrix<int_4>
385#pragma define_template TMatrix<int_8>
386#pragma define_template TMatrix<r_4>
[804]387#pragma define_template TMatrix<r_8>
[762]388#pragma define_template TMatrix< complex<r_4> >
389#pragma define_template TMatrix< complex<r_8> >
390#endif
391
392#if defined(ANSI_TEMPLATES) || defined(GNU_TEMPLATES)
393template class TMatrix<uint_2>;
394template class TMatrix<int_4>;
395template class TMatrix<int_8>;
396template class TMatrix<r_4>;
397template class TMatrix<r_8>;
398template class TMatrix< complex<r_4> >;
399template class TMatrix< complex<r_8> >;
400#endif
Note: See TracBrowser for help on using the repository browser.