source: Sophya/trunk/SophyaLib/SkyMap/spherehealpix.cc@ 2968

Last change on this file since 2968 was 2968, checked in by ansari, 19 years ago

Ajout methode ThetaOfSlice() a l'interface SphericalMap et propagation , Reza 06/06/2006

File size: 18.1 KB
Line 
1#include "sopnamsp.h"
2#include "machdefs.h"
3#include <math.h>
4#include <complex>
5
6#include "pexceptions.h"
7#include "fiondblock.h"
8#include "spherehealpix.h"
9#include "strutil.h"
10
11extern "C"
12{
13#include <stdio.h>
14#include <stdlib.h>
15#include <unistd.h>
16}
17
18using namespace SOPHYA;
19
20/*!
21 \class SOPHYA::SphereHEALPix
22 \ingroup SkyMap
23 \brief Spherical maps in HEALPix pixelisation scheme.
24
25 Class implementing spherical maps, in the HEALPix pixelisation scheme,
26 with template data types (double, float, complex, ...)
27
28
29\verbatim
30 Adapted from :
31 -----------------------------------------------------------------------
32 version 0.8.2 Aug97 TAC Eric Hivon, Kris Gorski
33 -----------------------------------------------------------------------
34
35 the sphere is split in 12 diamond-faces containing nside**2 pixels each
36 the numbering of the pixels (in the nested scheme) is similar to
37 quad-cube
38 In each face the first pixel is in the lowest corner of the diamond
39 the faces are (x,y) coordinate on each face
40
41 . . . . <--- North Pole
42 / \ / \ / \ / \ ^ ^
43 . 0 . 1 . 2 . 3 . <--- z = 2/3 \ /
44 \ / \ / \ / \ / y \ / x
45 4 . 5 . 6 . 7 . 4 <--- equator \ /
46 / \ / \ / \ / \ \/
47 . 8 . 9 .10 .11 . <--- z = -2/3 (0,0) : lowest corner
48 \ / \ / \ / \ /
49 . . . . <--- South Pole
50\endverbatim
51 phi:0 2Pi
52
53 in the ring scheme pixels are numbered along the parallels
54 the first parallel is the one closest to the north pole and so on
55 on each parallel, pixels are numbered starting from the one closest
56 to phi = 0
57
58 nside MUST be a power of 2 (<= 8192)
59
60*/
61
62/* --Methode-- */
63
64template<class T>
65SphereHEALPix<T>::SphereHEALPix() : pixels_(), sliceBeginIndex_(),
66 sliceLenght_()
67
68
69{
70 InitNul();
71}
72
73/*! \fn SOPHYA::SphereHEALPix::SphereHEALPix(int_4 m)
74
75 \param <m> : "nside" of the Healpix algorithm
76
77 The total number of pixels will be Npix = 12*nside**2
78
79 nside MUST be a power of 2 (<= 8192)
80*/
81
82template<class T>
83SphereHEALPix<T>::SphereHEALPix(int_4 m)
84
85{
86 InitNul();
87 Pixelize(m);
88 SetThetaSlices();
89}
90//! Copy constructor
91template<class T>
92SphereHEALPix<T>::SphereHEALPix(const SphereHEALPix<T>& s, bool share)
93 : pixels_(s.pixels_, share), sliceBeginIndex_(s.sliceBeginIndex_, share),
94 sliceLenght_(s.sliceLenght_, share)
95//--
96{
97 nSide_= s.nSide_;
98 nPix_ = s.nPix_;
99 omeg_ = s.omeg_;
100 if(s.mInfo_) this->mInfo_= new DVList(*s.mInfo_);
101}
102//++
103template<class T>
104SphereHEALPix<T>::SphereHEALPix(const SphereHEALPix<T>& s)
105 : pixels_(s.pixels_), sliceBeginIndex_(s.sliceBeginIndex_),
106 sliceLenght_(s.sliceLenght_)
107// copy constructor
108//--
109{
110 nSide_= s.nSide_;
111 nPix_ = s.nPix_;
112 omeg_ = s.omeg_;
113 if(s.mInfo_) this->mInfo_= new DVList(*s.mInfo_);
114 // CloneOrShare(s);
115}
116
117//! Clone if \b a is not temporary, share if temporary
118/*! \sa NDataBlock::CloneOrShare(const NDataBlock<T>&) */
119template<class T>
120void SphereHEALPix<T>::CloneOrShare(const SphereHEALPix<T>& a)
121{
122 nSide_= a.nSide_;
123 nPix_ = a.nPix_;
124 omeg_ = a.omeg_;
125 pixels_.CloneOrShare(a.pixels_);
126 sliceBeginIndex_.CloneOrShare(a.sliceBeginIndex_);
127 sliceLenght_.CloneOrShare(a.sliceLenght_);
128 if (this->mInfo_) {delete this->mInfo_; this->mInfo_ = NULL;}
129 if (a.mInfo_) this->mInfo_ = new DVList(*(a.mInfo_));
130}
131
132//! Share data with a
133template<class T>
134void SphereHEALPix<T>::Share(const SphereHEALPix<T>& a)
135{
136 nSide_= a.nSide_;
137 nPix_ = a.nPix_;
138 omeg_ = a.omeg_;
139 pixels_.Share(a.pixels_);
140 sliceBeginIndex_.Share(a.sliceBeginIndex_);
141 sliceLenght_.Share(a.sliceLenght_);
142 if (this->mInfo_) {delete this->mInfo_; this->mInfo_ = NULL;}
143 if (a.mInfo_) this->mInfo_ = new DVList(*(a.mInfo_));
144}
145
146////////////////////////// methodes de copie/share
147template<class T>
148SphereHEALPix<T>& SphereHEALPix<T>::Set(const SphereHEALPix<T>& a)
149{
150 if (this != &a)
151 {
152
153 if (a.NbPixels() < 1)
154 throw RangeCheckError("SphereHEALPix<T>::Set(a ) - SphereHEALPix a not allocated ! ");
155 if (NbPixels() < 1) CloneOrShare(a);
156 else CopyElt(a);
157
158
159 if (this->mInfo_) delete this->mInfo_;
160 this->mInfo_ = NULL;
161 if (a.mInfo_) this->mInfo_ = new DVList(*(a.mInfo_));
162 }
163 return(*this);
164}
165
166template<class T>
167SphereHEALPix<T>& SphereHEALPix<T>::CopyElt(const SphereHEALPix<T>& a)
168{
169 if (NbPixels() < 1)
170 throw RangeCheckError("SphereHEALPix<T>::CopyElt(const SphereHEALPix<T>& ) - Not Allocated SphereHEALPix ! ");
171 if (NbPixels() != a.NbPixels())
172 throw(SzMismatchError("SphereHEALPix<T>::CopyElt(const SphereHEALPix<T>&) SizeMismatch")) ;
173 nSide_= a.nSide_;
174 nPix_ = a.nPix_;
175 omeg_ = a.omeg_;
176 int k;
177 for (k=0; k< nPix_; k++) pixels_(k) = a.pixels_(k);
178 for (k=0; k< a.sliceBeginIndex_.Size(); k++) sliceBeginIndex_(k) = a.sliceBeginIndex_(k);
179 for (k=0; k< a.sliceLenght_.Size(); k++) sliceLenght_(k) = a.sliceLenght_(k);
180 return(*this);
181}
182
183
184
185//++
186// Titre Destructor
187//--
188//++
189template<class T>
190SphereHEALPix<T>::~SphereHEALPix()
191
192//--
193{
194}
195
196//++
197// Titre Public Methods
198//--
199
200/*! \fn void SOPHYA::SphereHEALPix::Resize(int_4 m)
201 \param <m> "nside" of the HEALPix algorithm
202
203 The total number of pixels will be Npix = 12*nside**2
204
205 nside MUST be a power of 2 (<= 8192)
206*/
207template<class T>
208void SphereHEALPix<T>::Resize(int_4 m)
209
210
211{
212 if ((m <= 0 && nSide_ > 0)) {
213 cout << "SphereHEALPix<T>::Resize(m) with m<=0, NOT resized" << endl;
214 return;
215 }
216 InitNul();
217 Pixelize(m);
218 SetThetaSlices();
219}
220
221template<class T>
222void SphereHEALPix<T>::Pixelize( int_4 m)
223
224// prépare la pixelisation Gorski (m a la même signification
225// que pour le constructeur)
226//
227//
228{
229 if (m<=0 || m> 8192) {
230 cout << "SphereHEALPix<T>::Pixelize() m=" << m <<" out of range [0,8192]" << endl;
231 throw ParmError("SphereHEALPix<T>::Pixelize() m out of range");
232 }
233 // verifier que m est une puissance de deux
234 int x= m;
235 while (x%2==0) x/=2;
236 if(x != 1) {
237 cout << "SphereHEALPix<T>::Pixelize() m=" << m << " != 2^n " << endl;
238 throw ParmError("SphereHEALPix<T>::Pixelize() m!=2^n");
239 }
240
241 // On memorise les arguments d'appel
242 nSide_= m;
243
244 // Nombre total de pixels sur la sphere entiere
245 nPix_= 12*nSide_*nSide_;
246
247 // pour le moment les tableaux qui suivent seront ranges dans l'ordre
248 // de l'indexation GORSKY "RING"
249 // on pourra ulterieurement changer de strategie et tirer profit
250 // de la dualite d'indexation GORSKY (RING et NEST) : tout dependra
251 // de pourquoi c'est faire
252
253 // Creation et initialisation du vecteur des contenus des pixels
254 pixels_.ReSize(nPix_);
255 pixels_.Reset();
256
257 // solid angle per pixel
258 omeg_= 4.0*Pi/nPix_;
259}
260
261template<class T>
262void SphereHEALPix<T>::InitNul()
263//
264// initialise à zéro les variables de classe
265{
266 nSide_= 0;
267 nPix_ = 0;
268 omeg_ = 0.;
269// pixels_.Reset(); - Il ne faut pas mettre les pixels a zero si share !
270}
271
272/* --Methode-- */
273/* Nombre de pixels du decoupage */
274/*! \fn int_4 SOPHYA::SphereHEALPix::NbPixels() const
275
276 Return number of pixels of the splitting
277*/
278template<class T>
279int_4 SphereHEALPix<T>::NbPixels() const
280{
281 return(nPix_);
282}
283
284
285/*! \fn uint_4 SOPHYA::SphereHEALPix::NbThetaSlices() const
286
287 \return number of slices in theta direction on the sphere
288*/
289template<class T>
290uint_4 SphereHEALPix<T>::NbThetaSlices() const
291{
292 uint_4 nbslices = uint_4(4*nSide_-1);
293 if (nSide_<=0)
294 {
295 nbslices = 0;
296 throw PException(" sphere not pixelized, NbSlice=0 ");
297 }
298 return nbslices;
299}
300
301//! Return the theta angle for slice defined by \b index
302template<class T>
303r_8 SphereHEALPix<T>::ThetaOfSlice(int_4 index) const
304{
305 uint_4 nbslices = uint_4(4*nSide_-1);
306 if (index<0 || index >= nbslices)
307 throw RangeCheckError(" SphereHEALPix::ThetaOfSlice() index out of range");
308 r_8 theta, phi0;
309 PixThetaPhi(sliceBeginIndex_(index), theta, phi0);
310 return theta;
311}
312
313/*! \fn void SOPHYA::SphereHEALPix::GetThetaSlice(int_4 index,r_8& theta,TVector<r_8>& phi,TVector<T>& value) const
314
315 For a theta-slice with index 'index', return :
316
317 the corresponding "theta"
318
319 a vector containing the phi's of the pixels of the slice
320
321 a vector containing the corresponding values of pixels
322*/
323template<class T>
324void SphereHEALPix<T>::GetThetaSlice(int_4 index,r_8& theta,TVector<r_8>& phi,TVector<T>& value) const
325
326{
327
328 if (index<0 || index >= NbThetaSlices())
329 {
330 cout << " SphereHEALPix::GetThetaSlice : Pixel index out of range" <<endl;
331 throw RangeCheckError(" SphereHEALPix::GetThetaSlice() index out of range");
332 }
333
334
335 int_4 iring= sliceBeginIndex_(index);
336 int_4 lring = sliceLenght_(index);
337
338 phi.ReSize(lring);
339 value.ReSize(lring);
340
341 double TH= 0.;
342 double FI= 0.;
343 for(int_4 kk = 0; kk < lring;kk++)
344 {
345 PixThetaPhi(kk+iring,TH,FI);
346 phi(kk)= FI;
347 value(kk)= PixVal(kk+iring);
348 }
349 theta= TH;
350}
351/*! \fn void SOPHYA::SphereHEALPix::GetThetaSlice(int_4 sliceIndex,r_8& theta, r_8& phi0, TVector<int_4>& pixelIndices,TVector<T>& value) const
352
353 For a theta-slice with index 'index', return :
354
355 the corresponding "theta"
356
357 the corresponding "phi" for first pixel of the slice
358
359 a vector containing indices of the pixels of the slice
360
361 (equally distributed in phi)
362
363 a vector containing the corresponding values of pixels
364*/
365
366template<class T>
367void SphereHEALPix<T>::GetThetaSlice(int_4 sliceIndex,r_8& theta, r_8& phi0, TVector<int_4>& pixelIndices,TVector<T>& value) const
368
369{
370
371 if (sliceIndex<0 || sliceIndex >= NbThetaSlices())
372 {
373 cout << " SphereHEALPix::GetThetaSlice : Pixel index out of range" <<endl;
374 throw RangeCheckError(" SphereHEALPix::GetThetaSlice : Pixel index out of range");
375 }
376 int_4 iring= sliceBeginIndex_(sliceIndex);
377 int_4 lring = sliceLenght_(sliceIndex);
378 pixelIndices.ReSize(lring);
379 value.ReSize(lring);
380
381 for(int_4 kk = 0; kk < lring;kk++)
382 {
383 pixelIndices(kk)= kk+iring;
384 value(kk)= PixVal(kk+iring);
385 }
386 PixThetaPhi(iring, theta, phi0);
387}
388
389template<class T>
390void SphereHEALPix<T>::SetThetaSlices()
391{
392 sliceBeginIndex_.ReSize(4*nSide_-1);
393 sliceLenght_.ReSize(4*nSide_-1);
394 int sliceIndex;
395 for (sliceIndex=0; sliceIndex< nSide_-1; sliceIndex++)
396 {
397 sliceBeginIndex_(sliceIndex) = 2*sliceIndex*(sliceIndex+1);
398 sliceLenght_(sliceIndex) = 4*(sliceIndex+1);
399 }
400 for (sliceIndex= nSide_-1; sliceIndex< 3*nSide_; sliceIndex++)
401 {
402 sliceBeginIndex_(sliceIndex) = 2*nSide_*(2*sliceIndex-nSide_+1);
403 sliceLenght_(sliceIndex) = 4*nSide_;
404 }
405 for (sliceIndex= 3*nSide_; sliceIndex< 4*nSide_-1; sliceIndex++)
406 {
407 int_4 nc= 4*nSide_-1-sliceIndex;
408 sliceBeginIndex_(sliceIndex) = nPix_-2*nc*(nc+1);
409 sliceLenght_(sliceIndex) = 4*nc;
410 }
411}
412
413
414/*! \fn T& SOPHYA::SphereHEALPix::PixVal(int_4 k)
415
416 \return value of pixel with "RING" index k
417*/
418template<class T>
419T& SphereHEALPix<T>::PixVal(int_4 k)
420
421{
422 if((k < 0) || (k >= nPix_))
423 {
424 throw RangeCheckError("SphereHEALPix::PIxVal Pixel index out of range");
425 }
426 return pixels_(k);
427}
428
429/*! \fn T const& SOPHYA::SphereHEALPix::PixVal(int_4 k) const
430
431 \return value of pixel with "RING" index k
432*/
433template<class T>
434T const& SphereHEALPix<T>::PixVal(int_4 k) const
435
436{
437 if((k < 0) || (k >= nPix_))
438 {
439 throw RangeCheckError("SphereHEALPix::PIxVal Pixel index out of range");
440 }
441 return *(pixels_.Data()+k);
442}
443
444/*! \fn T& SOPHYA::SphereHEALPix::PixValNest(int_4 k)
445
446 \return value of pixel with "NESTED" index k
447*/
448template<class T>
449T& SphereHEALPix<T>::PixValNest(int_4 k)
450
451//--
452{
453 if((k < 0) || (k >= nPix_))
454 {
455 throw RangeCheckError("SphereHEALPix::PIxValNest Pixel index out of range");
456 }
457 return pixels_(nest2ring(nSide_,k));
458}
459
460/*! \fn T const& SOPHYA::SphereHEALPix::PixValNest(int_4 k) const
461
462 \return value of pixel with "NESTED" index k
463*/
464
465template<class T>
466T const& SphereHEALPix<T>::PixValNest(int_4 k) const
467
468{
469 if((k < 0) || (k >= nPix_))
470 {
471 throw RangeCheckError("SphereHEALPix::PIxValNest Pixel index out of range");
472 }
473 int_4 pix= nest2ring(nSide_,k);
474 return *(pixels_.Data()+pix);
475}
476
477/*! \fn bool SOPHYA::SphereHEALPix::ContainsSph(double theta, double phi) const
478
479\return true if teta,phi in map
480*/
481template<class T>
482bool SphereHEALPix<T>::ContainsSph(double theta, double phi) const
483{
484return(true);
485}
486
487/*! \fn int_4 SOPHYA::SphereHEALPix::PixIndexSph(double theta,double phi) const
488
489 \return "RING" index of the pixel corresponding to direction (theta, phi).
490 */
491template<class T>
492int_4 SphereHEALPix<T>::PixIndexSph(double theta,double phi) const
493
494{
495 return ang2pix_ring(nSide_,theta,phi);
496}
497
498/*! \fn int_4 SOPHYA::SphereHEALPix::PixIndexSphNest(double theta,double phi) const
499
500 \return "NESTED" index of the pixel corresponding to direction (theta, phi).
501 */
502template<class T>
503int_4 SphereHEALPix<T>::PixIndexSphNest(double theta,double phi) const
504
505{
506 return ang2pix_nest(nSide_,theta,phi);
507}
508
509
510/* --Methode-- */
511/*! \fn void SOPHYA::SphereHEALPix::PixThetaPhi(int_4 k,double& theta,double& phi) const
512 \return (theta,phi) coordinates of middle of pixel with "RING" index k
513 */
514template<class T>
515void SphereHEALPix<T>::PixThetaPhi(int_4 k,double& theta,double& phi) const
516{
517 pix2ang_ring(nSide_,k,theta,phi);
518}
519
520/*! \fn T SOPHYA::SphereHEALPix::SetPixels(T v)
521
522Set all pixels to value v
523*/
524template <class T>
525T SphereHEALPix<T>::SetPixels(T v)
526{
527pixels_.Reset(v);
528return(v);
529}
530
531
532
533/*! \fn void SOPHYA::SphereHEALPix::PixThetaPhiNest(int_4 k,double& theta,double& phi) const
534
535 \return (theta,phi) coordinates of middle of pixel with "NESTED" index k
536 */
537template<class T>
538void SphereHEALPix<T>::PixThetaPhiNest(int_4 k,double& theta,double& phi) const
539
540{
541 pix2ang_nest(nSide_,k,theta,phi);
542}
543
544
545/*! \fn int_4 SOPHYA::SphereHEALPix::NestToRing(int_4 k) const
546
547 translation from NESTED index into RING index
548*/
549template<class T>
550int_4 SphereHEALPix<T>::NestToRing(int_4 k) const
551
552{
553 return nest2ring(nSide_,k);
554}
555
556
557/*! \fn int_4 SOPHYA::SphereHEALPix::RingToNest(int_4 k) const
558
559 translation from RING index into NESTED index
560*/
561template<class T>
562int_4 SphereHEALPix<T>::RingToNest(int_4 k) const
563{
564 return ring2nest(nSide_,k);
565}
566
567// ...... Operations de calcul ......
568
569//! Fill a SphereHEALPix with a constant value \b a
570template <class T>
571SphereHEALPix<T>& SphereHEALPix<T>::SetT(T a)
572{
573 if (NbPixels() < 1)
574 throw RangeCheckError("SphereHEALPix<T>::SetT(T ) - SphereHEALPix not dimensionned ! ");
575 pixels_ = a;
576 return (*this);
577}
578
579/*! Add a constant value \b x to a SphereHEALPix */
580template <class T>
581SphereHEALPix<T>& SphereHEALPix<T>::Add(T a)
582 {
583 cout << " c'est mon Add " << endl;
584 if (NbPixels() < 1)
585 throw RangeCheckError("SphereHEALPix<T>::Add(T ) - SphereHEALPix not dimensionned ! ");
586 // pixels_ += a;
587 pixels_.Add(a);
588 return (*this);
589}
590
591/*! Substract a constant value \b a to a SphereHEALPix */
592template <class T>
593SphereHEALPix<T>& SphereHEALPix<T>::Sub(T a,bool fginv)
594{
595 if (NbPixels() < 1)
596 throw RangeCheckError("SphereHEALPix<T>::Sub(T ) - SphereHEALPix not dimensionned ! ");
597 pixels_.Sub(a,fginv);
598 return (*this);
599}
600
601/*! multiply a SphereHEALPix by a constant value \b a */
602template <class T>
603SphereHEALPix<T>& SphereHEALPix<T>::Mul(T a)
604{
605 if (NbPixels() < 1)
606 throw RangeCheckError("SphereHEALPix<T>::Mul(T ) - SphereHEALPix not dimensionned ! ");
607 pixels_ *= a;
608 return (*this);
609}
610
611/*! divide a SphereHEALPix by a constant value \b a */
612template <class T>
613SphereHEALPix<T>& SphereHEALPix<T>::Div(T a)
614{
615 if (NbPixels() < 1)
616 throw RangeCheckError("SphereHEALPix<T>::Div(T ) - SphereHEALPix not dimensionned ! ");
617 pixels_ /= a;
618 return (*this);
619}
620
621// >>>> Operations avec 2nd membre de type SphereHEALPix
622//! Add two SphereHEALPix
623
624template <class T>
625SphereHEALPix<T>& SphereHEALPix<T>::AddElt(const SphereHEALPix<T>& a)
626{
627 if (NbPixels() != a.NbPixels() )
628 {
629 throw(SzMismatchError("SphereHEALPix<T>::AddElt(const SphereHEALPix<T>&) SizeMismatch")) ;
630 }
631 pixels_ += a.pixels_;
632 return (*this);
633}
634
635//! Substract two SphereHEALPix
636template <class T>
637SphereHEALPix<T>& SphereHEALPix<T>::SubElt(const SphereHEALPix<T>& a)
638{
639 if (NbPixels() != a.NbPixels() )
640 {
641 throw(SzMismatchError("SphereHEALPix<T>::SubElt(const SphereHEALPix<T>&) SizeMismatch")) ;
642 }
643 pixels_ -= a.pixels_;
644 return (*this);
645}
646
647//! Multiply two SphereHEALPix (elements by elements)
648template <class T>
649SphereHEALPix<T>& SphereHEALPix<T>::MulElt(const SphereHEALPix<T>& a)
650{
651 if (NbPixels() != a.NbPixels() )
652 {
653 throw(SzMismatchError("SphereHEALPix<T>::MulElt(const SphereHEALPix<T>&) SizeMismatch")) ;
654 }
655 pixels_ *= a.pixels_;
656 return (*this);
657}
658
659//! Divide two SphereHEALPix (elements by elements) - No protection for divide by 0
660template <class T>
661SphereHEALPix<T>& SphereHEALPix<T>::DivElt(const SphereHEALPix<T>& a)
662{
663 if (NbPixels() != a.NbPixels() )
664 {
665 throw(SzMismatchError("SphereHEALPix<T>::DivElt(const SphereHEALPix<T>&) SizeMismatch")) ;
666 }
667 pixels_ /= a.pixels_;
668 return (*this);
669}
670
671
672
673
674template <class T>
675void SphereHEALPix<T>::print(ostream& os) const
676{
677 if(this->mInfo_) os << " DVList Info= " << *(this->mInfo_) << endl;
678 //
679 os << " nSide_ = " << nSide_ << endl;
680 os << " nPix_ = " << nPix_ << endl;
681 os << " omeg_ = " << omeg_ << endl;
682
683 os << " content of pixels : ";
684 for(int i=0; i < nPix_; i++)
685 {
686 if(i%5 == 0) os << endl;
687 os << pixels_(i) <<", ";
688 }
689 os << endl;
690
691
692}
693
694
695
696//*******************************************************************
697
698#ifdef __CXX_PRAGMA_TEMPLATES__
699#pragma define_template SphereHEALPix<uint_2>
700#pragma define_template SphereHEALPix<int_4>
701#pragma define_template SphereHEALPix<r_8>
702#pragma define_template SphereHEALPix<r_4>
703#pragma define_template SphereHEALPix< complex<r_4> >
704#pragma define_template SphereHEALPix< complex<r_8> >
705#endif
706#if defined(ANSI_TEMPLATES) || defined(GNU_TEMPLATES)
707namespace SOPHYA {
708template class SphereHEALPix<uint_2>;
709template class SphereHEALPix<int_4>;
710template class SphereHEALPix<r_8>;
711template class SphereHEALPix<r_4>;
712template class SphereHEALPix< complex<r_4> >;
713template class SphereHEALPix< complex<r_8> >;
714}
715#endif
716
Note: See TracBrowser for help on using the repository browser.