source: Sophya/trunk/SophyaLib/BaseTools/ndatablock.cc@ 245

Last change on this file since 245 was 245, checked in by ansari, 26 years ago

creation NDataBlock, + remove .h unused rz+cmv 22/4/99

File size: 12.6 KB
Line 
1#include "machdefs.h"
2#include <stdio.h>
3#include <stdlib.h>
4#include <iostream.h>
5#include <complex>
6#include "pexceptions.h"
7#include "ndatablock.h"
8
9#define DEBUG_NDATABLOCK
10
11#ifdef DEBUG_NDATABLOCK
12 static size_t NallocData = 0;
13 static size_t NallocSRef = 0;
14#endif
15
16// LOGIQUE DE BASE:
17// - le createur par copie et la surcharge de l operateur = "partage" les donnees
18// - gestion du partage de reference
19
20//************ Createur, Destructeur, gestion des donnees
21
22template <class T>
23NDataBlock<T>::NDataBlock(size_t n)
24// Createur d'une structure de "n" donnees
25: mSz(0), mSRef(NULL), mIsTemp(false)
26{
27Alloc(n);
28}
29
30template <class T>
31NDataBlock<T>::NDataBlock(size_t n, T* data, Bridge* br)
32// Createur d'une structure de "n" donnees, avec donnees preallouees
33: mSz(0), mSRef(NULL), mIsTemp(false)
34{
35Alloc(n,data,br);
36}
37
38template <class T>
39NDataBlock<T>::NDataBlock()
40// Createur par default
41: mSz(0), mSRef(NULL), mIsTemp(false)
42{
43}
44
45template <class T>
46NDataBlock<T>::NDataBlock(NDataBlock<T>& a)
47// Createur par copie
48// ATTENTION: partage les donnees avec "a"
49// Ecriture: NDataBlock a = b;
50// NDataBlock a(b)
51: mSz(0), mSRef(NULL), mIsTemp(false)
52{
53Share(a);
54}
55
56template <class T>
57NDataBlock<T>::NDataBlock(NDataBlock<T>& a,bool share)
58// Createur avec choix de partager ou non
59: mSz(0), mSRef(NULL), mIsTemp(false)
60{
61if(share) Share(a); else Clone(a);
62}
63
64template <class T>
65NDataBlock<T>::~NDataBlock()
66// Destructeur
67{
68Delete();
69}
70
71template <class T>
72void NDataBlock<T>::Alloc(size_t n,T* data,Bridge* br)
73// Allocation d'un NOUVEL espace de stoquage
74// Si data==NULL : allocation de l'espace memoire
75// data!=NULL : partage des donnees avec l'adresse data
76// Si br==NULL : les donnees nous appartiennent
77// br!=NULL : les donnees ne nous appartiennent pas (ex Blitz)
78{
79#ifdef DEBUG_NDATABLOCK
80cout<<"NDataBlock::Alloc("<<n<<") mSRef="<<mSRef<<endl;
81#endif
82if(n==0) throw(SzMismatchError("NDataBlock::Alloc n==0\n"));
83if(mSRef) Delete();
84mSz = n;
85mSRef = new NDREF;
86mSRef->nref = 1;
87if(data) mSRef->data = data; else mSRef->data = new T[n];
88mSRef->bridge = br;
89#ifdef DEBUG_NDATABLOCK
90if(!data) NallocData++; NallocSRef++;
91cout<<"NDataBlock::Alloc("<<n<<") mSRef="<<mSRef
92 <<" mSRef->nref"<<mSRef->nref<<" mSRef->data"<< mSRef->data
93 <<" Total("<<NallocData<<","<<NallocSRef<<")"<<endl;
94#endif
95}
96
97template <class T>
98void NDataBlock<T>::Clone(NDataBlock<T>& a)
99// Clone (copie de donnee) a partir de "a"
100{
101#ifdef DEBUG_NDATABLOCK
102cout<<"NDataBlock::Clone("<<&a<<endl;
103#endif
104if(!a.mSRef) {mSz=0; mSRef=NULL;} // cas ou "a" est cree par defaut
105else if(a.IsTemp()) Share(a);
106else {Alloc(a.mSz); memcpy(Dtata(),a.Dtata(),mSz*sizeof(T));}
107}
108
109template <class T>
110void NDataBlock<T>::Share(NDataBlock<T>& a)
111// Partage des donnees avec "a"
112{
113#ifdef DEBUG_NDATABLOCK
114cout<<"NDataBlock::Share("<<&a<<") a.mSRef="<<a.mSRef<<" mSRef="<<mSRef<<endl;
115#endif
116if(&a==NULL) throw(NullPtrError("NDataBlock::Share &a==NULL\n"));
117// on ne peut partager si "a" pas alloue
118if(!a.mSRef) throw(NullPtrError("NDataBlock::Share not allocated a\n"));
119if(mSRef) Delete();
120mSz = a.mSz; mSRef = a.mSRef; mSRef->nref++;
121#ifdef DEBUG_NDATABLOCK
122cout<<"...NDataBlock::Share("<<&a<<") mSRef="<<mSRef
123 <<" mSRef->nref"<<mSRef->nref<<" mSRef->data"<< mSRef->data<<endl;
124#endif
125}
126
127template <class T>
128void NDataBlock<T>::Delete(void)
129// Pour detruire les pointeurs en tenant compte des references
130{
131#ifdef DEBUG_NDATABLOCK
132cout<<"NDataBlock::Delete() mSRef="<<mSRef;
133if(mSRef) cout<<" mSRef->nref"<<mSRef->nref<<" mSRef->data"<<mSRef->data;
134cour<<endl;
135#endif
136if(mSRef==NULL) return; // cas du createur par defaut
137mSRef->nref--;
138if(mSRef->nref != 0) {
139#ifdef DEBUG_NDATABLOCK
140 cout<<"...NDataBlock::Delete() pas de desallocation il reste nref="<<mSRef->nref<<endl;
141#endif
142 return;
143}
144#ifdef DEBUG_NDATABLOCK
145if(!mSRef->bridge) NallocData--; NallocSRef--;
146cout<<"...NNDataBlock::Delete() desallocation complete il reste nref="<<mSRef->nref
147 <<" Total("<<NallocData<<","<<NallocSRef<<")"<<endl;
148#endif
149// Si il y a un Bridge les donnees ne n'appartiennent pas, on detruit le Bridge
150if(mSRef->bridge) delete mSRef->bridge;
151// sinon, les donnees ont ete allouees par nos soins, on libere l'espace memoire
152else delete [] mSRef->data;
153mSRef->bridge=NULL; mSRef->data=NULL;
154delete mSRef; mSRef=NULL;
155}
156
157template <class T>
158void NDataBlock<T>::ReSize(size_t n)
159// Re-dimension, dans ce cas re-allocation de la place
160{
161Alloc(n);
162}
163
164//**** Impression
165
166template <class T>
167void NDataBlock<T>::Print(size_t i1,size_t n)
168// Impression de n elements a partir de i1
169{
170size_t nr = 0;
171T* p = NULL;
172if(mSRef) {nr = mSRef->nref; p = mSRef->data;}
173cout<<"NDataBlock::Print nel=%ld nref=%d (%p)\n",mSz,nr,p;
174if(i1<0 || i1>=mSz || n<=0 || !p) return;
175size_t i2 = i1+n; if(i2>mSz) i2=mSz;
176size_t im = 1;
177while(i1<i2) {
178 cout<<" "<<(*this)(i1); i1++;
179 if(im==10) {cout<<"\n"; im=1;} else im++;
180}
181}
182
183//**** Surcharge de = : NDataBlock=NDataBlock; NDataBlock=<T> b;
184
185template <class T>
186NDataBlock<T>& NDataBlock<T>::operator = (const NDataBlock<T>& a)
187// surcharge avec partage des donnees
188// Ecriture: NDataBlock a; a = b;
189// NDataBlock a(10); a = b; (a est re-affecte)
190{
191if(this == &a) return *this;
192if(a.mSz!=mSz) throw(SzMismatchError("NDataBlock::operator=A size mismatch/null\n"));
193Share(a);
194return *this;
195}
196
197template <class T>
198NDataBlock<T>& NDataBlock<T>::operator = (const T v)
199// surcharge avec copie des donnees (pas de partage)
200// "this" est sur-ecrit, attention au partage de reference!
201// NDataBlock a; a = v; ou bien NDataBlock a(10); a = v;
202{
203if(mSz==0) throw(SzMismatchError("NDataBlock::operator=v null size\n"));
204T* p=Begin(), pe=End();
205while (p<pe) *p++ = v;
206return *this;
207}
208
209//**** Surcharge de +=,-=,*=,/= (INPLACE): NDataBlock += <T> b;
210
211template <class T>
212NDataBlock<T>& NDataBlock<T>::operator += (T b)
213{
214if(mSz==0) throw(SzMismatchError("NDataBlock::operator+=v null size\n"));
215T* p=Begin(), pe=End();
216while (p<pe) *p++ += b;
217return *this;
218}
219
220template <class T>
221NDataBlock<T>& NDataBlock<T>::operator -= (T b)
222{
223if(mSz==0) throw(SzMismatchError("NDataBlock::operator-=v null size\n"));
224T* p=Begin(), pe=End();
225while (p<pe) *p++ -= b;
226return *this;
227}
228
229template <class T>
230NDataBlock<T>& NDataBlock<T>::operator *= (T b)
231{
232if(mSz==0) throw(SzMismatchError("NDataBlock::operator*=v null size\n"));
233T* p=Begin(), pe=End();
234while (p<pe) *p++ *= b;
235return *this;
236}
237
238template <class T>
239NDataBlock<T>& NDataBlock<T>::operator /= (T b)
240{
241if(b==(<T>) 0) throw(ParmError("NDataBlock::operator/=v divide by zero\n"));
242if(mSz==0) throw(SzMismatchError("NDataBlock::operator/=v null size\n"));
243T* p=Begin(), pe=End();
244while (p<pe) *p++ /= b;
245return *this;
246}
247
248//**** Surcharge de +=,-=,*=,/= (INPLACE): NDataBlock += NDataBlock;
249
250template <class T>
251NDataBlock<T>& NDataBlock<T>::operator += (const NDataBlock<T>& a)
252{
253if(mSz==0 || mSz!=a.mSz) throw(SzMismatchError("NDataBlock::operator+=A size mismatch/null"));
254T* p=Begin(), pe=End(), pa=a.Begin();
255while (p<pe) *p++ += *pa++; // ca marche meme si *this=a
256return *this;
257}
258
259template <class T>
260NDataBlock<T>& NDataBlock<T>::operator -= (const NDataBlock<T>& a)
261{
262if(mSz==0 || mSz!=a.mSz) throw(SzMismatchError("NDataBlock::operator-=A size mismatch/null"));
263T* p=Begin(), pe=End(), pa=a.Begin();
264while (p<pe) *p++ -= *pa++; // ca marche meme si *this=a
265return *this;
266}
267
268template <class T>
269NDataBlock<T>& NDataBlock<T>::operator *= (const NDataBlock<T>& a)
270{
271if(mSz==0 || mSz!=a.mSz) throw(SzMismatchError("NDataBlock::operator*=A size mismatch/null"));
272T* p=Begin(), pe=End(), pa=a.Begin();
273while (p<pe) *p++ *= *pa++; // ca marche meme si *this=a
274return *this;
275}
276
277template <class T>
278NDataBlock<T>& NDataBlock<T>::operator /= (const NDataBlock<T>& a)
279{
280if(mSz==0 || mSz!=a.mSz) throw(SzMismatchError("NDataBlock::operator/=A size mismatch/null"));
281T* p=Begin(), pe=End(), pa=a.Begin();
282while (p<pe) *p++ /= *pa++;
283return *this;
284}
285
286//**** FIN DES METHODES DE LA CLASSE
287
288//**** Surcharge de +,-,*,/ : NDataBlock = NDataBlock+<T>b; NDataBlock = <T>b+NDataBlock;
289// ATTENTION: re-affectation imposee
290
291template <class T>
292NDataBlock<T> operator + (const NDataBlock<T>& a, T b)
293{
294NDataBlock<T> result(a,false); result.SetTemp(true);
295return (result += b);
296}
297
298template <class T>
299NDataBlock<T> operator + (T b, const NDataBlock<T>& a)
300{
301NDataBlock<T> result(a,false); result.SetTemp(true);
302return (result += b);
303}
304
305template <class T>
306NDataBlock<T> operator - (const NDataBlock<T>& a, T b)
307{
308NDataBlock<T> result(a,false); result.SetTemp(true);
309return (result -= b);
310}
311
312template <class T>
313NDataBlock<T> operator - (T b, const NDataBlock<T>& a)
314{
315NDataBlock<T> result(a,false); result.SetTemp(true);
316T* p=result.Begin(), pe=result.End(), pa=a.Begin();
317while(p<pe) {*p++ = b - *pa++;}
318return result;
319}
320
321template <class T>
322NDataBlock<T> operator * (const NDataBlock<T>& a, T b)
323{
324NDataBlock<T> result(a,false); result.SetTemp(true);
325return (result *= b);
326}
327
328template <class T>
329NDataBlock<T> operator * (T b, const NDataBlock<T>& a)
330{
331NDataBlock<T> result(a,false); result.SetTemp(true);
332return (result *= b);
333}
334
335template <class T>
336NDataBlock<T> operator / (const NDataBlock<T>& a, T b)
337{
338NDataBlock<T> result(a,false); result.SetTemp(true);
339return (result /= b);
340}
341
342template <class T>
343NDataBlock<T> operator / (T b, const NDataBlock<T>& a)
344{
345NDataBlock<T> result(a,false); result.SetTemp(true);
346T* p=result.Begin(), pe=result.End(), pa=a.Begin();
347while(p<pe) {*p++ = b / *pa++;}
348return result;
349}
350
351//**** Surcharge de +,-,*,/ : NDataBlock = NDataBlock+NDataBlock;
352
353template <class T>
354NDataBlock<T> operator + (const NDataBlock<T>& a, const NDataBlock<T>& b)
355{
356if(a.mSz!=b.mSz) throw(SzMismatchError("NDataBlock operator C=A+B size mismatch/null\n"));
357if(b.IsTemp()) {
358 NDataBlock<T> result(b,true); result.SetTemp(true);
359 return result += a;
360} else {
361 NDataBlock<T> result(a,false); result.SetTemp(true);
362 return result += b;
363}
364}
365
366template <class T>
367NDataBlock<T> operator * (const NDataBlock<T>& a, const NDataBlock<T>& b)
368{
369if(a.mSz!=b.mSz) throw(SzMismatchError("NDataBlock operator C=A*B size mismatch/null\n"));
370if(b.IsTemp()) {
371 NDataBlock<T> result(b,true); result.SetTemp(true);
372 return result *= a;
373} else {
374 NDataBlock<T> result(a,false); result.SetTemp(true);
375 return result *= b;
376}
377}
378
379template <class T>
380NDataBlock<T> operator - (const NDataBlock<T>& a, const NDataBlock<T>& b)
381{
382if(a.mSz!=b.mSz) throw(SzMismatchError("NDataBlock operator C=A-B size mismatch/null\n"));
383if(b.IsTemp()) {
384 NDataBlock<T> result(b,true); result.SetTemp(true);
385 T* p=result.Begin(), pe=result.End(), pa=a.Begin();
386 while(p<pe) {*p = *pa++ - *p; p++;}
387 return result;
388} else {
389 NDataBlock<T> result(a,false); result.SetTemp(true);
390 return result -= b;
391}
392}
393
394template <class T>
395NDataBlock<T> operator / (const NDataBlock<T>& a, const NDataBlock<T>& b)
396{
397if(a.mSz!=b.mSz) throw(SzMismatchError("NDataBlock operator C=A/B size mismatch/null\n"));
398if(b.IsTemp()) {
399 NDataBlock<T> result(b,true); result.SetTemp(true);
400 T* p=result.Begin(), pe=result.End(), pa=a.Begin();
401 while(p<pe) {*p = *pa++ / *p; p++;}
402 return result;
403} else {
404 NDataBlock<T> result(a,false); result.SetTemp(true);
405 return result /= b;
406}
407}
408
409
410
411
412#ifdef __CXX_PRAGMA_TEMPLATES__
413#pragma define_template NDataBlock<uint_1>
414#pragma define_template NDataBlock<uint_2>
415#pragma define_template NDataBlock<int_2>
416#pragma define_template NDataBlock<int_4>
417#pragma define_template NDataBlock<int_8>
418#pragma define_template NDataBlock<uint_2>
419#pragma define_template NDataBlock<uint_4>
420#pragma define_template NDataBlock<uint_8>
421#pragma define_template NDataBlock<r_4>
422#pragma define_template NDataBlock<r_8>
423#pragma define_template NDataBlock<complex<float>>
424#pragma define_template NDataBlock<complex<double>>
425#endif
426
427#ifdef __GNU_TEMPLATES__
428template class NDataBlock<uint_1>;
429template class NDataBlock<uint_2>;
430template class NDataBlock<int_2>;
431template class NDataBlock<int_4>;
432template class NDataBlock<int_8>;
433template class NDataBlock<uint_2>;
434template class NDataBlock<uint_4>;
435template class NDataBlock<uint_8>;
436template class NDataBlock<r_4>;
437template class NDataBlock<r_8>;
438template class NDataBlock<complex<float>>;
439template class NDataBlock<complex<double>>;
440#endif
441
442#if defined(__ANSI_TEMPLATES__)
443template class NDataBlock<uint_1>;
444template class NDataBlock<uint_2>;
445template class NDataBlock<int_2>;
446template class NDataBlock<int_4>;
447template class NDataBlock<int_8>;
448template class NDataBlock<uint_2>;
449template class NDataBlock<uint_4>;
450template class NDataBlock<uint_8>;
451template class NDataBlock<r_4>;
452template class NDataBlock<r_8>;
453template class NDataBlock<complex<float>>;
454template class NDataBlock<complex<double>>;
455#endif
456
457#ifdef __CXX_PRAGMA_TEMPLATES__
458#pragma define_template template<class uint_1> NDataBlock<uint_1> operator + (const NDataBlock<uint_1>& a, uint_1 b);
459#endif
460
461#ifdef __GNU_TEMPLATES__
462#endif
463
464#if defined(__ANSI_TEMPLATES__)
465#endif
Note: See TracBrowser for help on using the repository browser.