OSHUN  beta
Arbitrary Order Spherical-Harmonic 1D-3P Vlasov-Fokker-Planck-Maxwell code
state.cpp
Go to the documentation of this file.
1 
40 //--------------------------------------------------------------
41 
42 // Standard Libraries
43 #include <iostream>
44 #include <vector>
45 #include <valarray>
46 #include <complex>
47 
48 // My Libraries
49 #include "lib-array.h"
50 #include "lib-algorithms.h"
51 
52 // Declerations
53 #include "state.h"
54 #include "nmethods.h"
55 
56 //--------------------------------------------------------------
57 // Definition of the 1D spherical harmonic
58 //--------------------------------------------------------------
59 // Constructor and Destructor
60 //--------------------------------------------------------------
61 
62 // Constructor
63 SHarmonic1D::SHarmonic1D(size_t nump, size_t numx) {
65 }
66 // Copy constructor
68  sh = new Array2D<complex<double> >(other.nump(),other.numx());
69  *sh = other.array();
70 }
71 // Destructor
73  delete sh;
74 }
75 
76 //--------------------------------------------------------------
77 // Operators
78 //--------------------------------------------------------------
79 
80 // Copy assignment operator
81 SHarmonic1D& SHarmonic1D::operator=(const complex<double> & d){
82  *sh = d;
83  return *this;
84 }
86  if (this != &other) { //self-assignment
87  *sh = other.array();
88  }
89  return *this;
90 }
91 // *=
92 SHarmonic1D& SHarmonic1D::operator*=(const complex<double> & d){
93  (*sh) *=d;
94  return *this;
95 }
97  (*sh) *= shmulti.array();
98  return *this;
99 }
100 // +=
101 SHarmonic1D& SHarmonic1D::operator+=(const complex<double> & d){
102  (*sh) +=d;
103  return *this;
104 }
106  (*sh) += shadd.array();
107  return *this;
108 }
109 // -=
110 SHarmonic1D& SHarmonic1D::operator-=(const complex<double> & d){
111  (*sh) -=d;
112  return *this;
113 }
115  (*sh) -= shmin.array();
116  return *this;
117 }
118 
119 //--------------------------------------------------------------
120 // Other Algebra
121 //--------------------------------------------------------------
122 SHarmonic1D& SHarmonic1D::mpaxis(const valarray <complex<double> > & shmulti){
123  (*sh).multid1(shmulti);
124  return *this;
125 }
126 SHarmonic1D& SHarmonic1D::mxaxis(const valarray <complex<double> > & shmulti){
127  (*sh).multid2(shmulti);
128  return *this;
129 }
131  for (int i(0); i < dim(); ++i) {
132  (*sh)(i) = (*sh)(i).real();
133  }
134  return *this;
135 }
136 //--------------------------------------------------------------
137 
138 // P-difference
140  //--------------------------------------------------------//
141  //--------------------------------------------------------//
143  valarray <complex<double> > plast(this->numx());
144 
145  for (size_t i(0); i < plast.size(); ++i) {
146  plast[i] = (*sh)(nump()-2,i) - (*sh)(nump()-1,i);
147  }
148  *sh = (*sh).Dd1();
149  for (size_t i(0); i < plast.size(); ++i) {
150  // TODO The Dp at the zeroth cell is taken care off
151  // (*sh)(0,i) = 0.0; //separately, both for the E-field and the collisions.
152  (*sh)(nump()-1,i) = 2.0*plast[i];
153  }
154 
155  //--------------------------------------------------------//
156  //--------------------------------------------------------//
158  // Array2D<complex<double> > df((*this).nump(),(*this).numx());
159 
160  // for (long i2(0); i2<numx();++i2){
161 
162  // df(0,i2) = (*this)(1,i2)-(*this)(0,i2);
163  // df(1,i2) = 1.0/12.0*((*this)(4,i2)-6.0*(*this)(3,i2)+18.0*(*this)(2,i2)-10.0*(*this)(1,i2)-3.0*(*this)(0,i2));
164 
165  // for (long i1(2); i1<nump()-2;++i1){
166  // df(i1,i2) = 1.0/12.0*(-(*this)(i1+2,i2)+8.0*(*this)(i1+1,i2)-8.0*(*this)(i1-1,i2)+(*this)(i1-2,i2));
167  // }
168 
169  // df(nump()-2,i2) = 0.0; //1.0/12.0*(3.0*(*this)(nump()-1,i2)+10.0*(*this)(nump()-2,i2)-18.0*(*this)(nump()-3,i2)+6.0*(*this)(nump()-4,i2)-(*this)(nump()-5,i2));
170  // df(nump()-1,i2) = 0.0; //(*this)(nump()-1,i2)-(*this)(nump()-2,i2);
171 
172  // }
173 
174  // for (long i2(0); i2<numx();++i2) {
175  // for (long i1(0); i1 < nump(); ++i1) {
176  // (*this)(i1, i2) = -2.0*df(i1, i2);
177  // }
178  // }
179 
180  return *this;
181 }
182 //--------------------------------------------------------------
183 
184 // X-difference
186 
187  //--------------------------------------------------------//
188  //--------------------------------------------------------//
190  // for (size_t ix(0); ix < this->numx(); ++ix) {
191  // for (size_t ip(0); ip < this->nump(); ++ip) {
192  // (*sh)(ip,ix) = ix;
193  // }
194  // }
195  *sh = (*sh).Dd2(); // Worry about boundaries elsewhere
196 
197  // for (size_t ix(0); ix < this->numx(); ++ix) {
198  // for (size_t ip(0); ip < this->nump(); ++ip) {
199  // std::cout << "*sh(" << ip << "," << ix << ")" << (*sh)(ip,ix) << "\n";
200  // }
201  // }
202 
203 
204  //--------------------------------------------------------//
205  //--------------------------------------------------------//
206 
207  return *this;
208 }
209 //--------------------------------------------------------------
210 
211 // Filter Pcells
213  *sh = (*sh).Filterd1(N);
214  return *this;
215 }
216 
217 // Debug
219 
220  for (size_t i(0); i<numx();++i){
221  for (size_t p(0); p<nump();++p){
222  if ((isnan((*sh)(p,i).real())) || (isnan((*sh)(p,i).imag())))
223  {
224  std::cout << "NaN @ (" << p << "," << i << ")\n";
225  exit(1);
226  }
227  }
228  }
229 // std::cout << "SH OK! \n";
230  return;
231 
232 
233 }
234 
235 //**************************************************************
236 
237 //**************************************************************
238 // Definition of the 2D spherical harmonic
239 //--------------------------------------------------------------
240 // Constructor and Destructor
241 //--------------------------------------------------------------
242 
243 // Constructor
244 SHarmonic2D::SHarmonic2D(size_t nump, size_t numx, size_t numy) {
245  sh = new Array3D <complex <double> >(nump,numx,numy);
246 }
247 // Copy constructor
249  sh = new Array3D < complex <double> >(other.nump(),other.numx(),other.numy());
250  *sh = other.array();
251 }
252 // Destructor
254  delete sh;
255 }
256 
257 //--------------------------------------------------------------
258 // Operators
259 //--------------------------------------------------------------
260 
261 // Copy assignment operator
262 SHarmonic2D& SHarmonic2D::operator=(const complex<double>& d){
263  *sh = d;
264  return *this;
265 }
267  if (this != &other) { //self-assignment
268  *sh = other.array();
269  }
270  return *this;
271 }
272 // *=
273 SHarmonic2D& SHarmonic2D::operator*=(const complex<double>& d){
274  (*sh) *=d;
275  return *this;
276 }
278  (*sh) *= shmulti.array();
279  return *this;
280 }
281 // +=
282 SHarmonic2D& SHarmonic2D::operator+=(const complex<double>& d){
283  (*sh) +=d;
284  return *this;
285 }
287  (*sh) += shadd.array();
288  return *this;
289 }
290 // -=
291 SHarmonic2D& SHarmonic2D::operator-=(const complex<double>& d){
292  (*sh) -=d;
293  return *this;
294 }
296  (*sh) -= shmin.array();
297  return *this;
298 }
299 
300 //--------------------------------------------------------------
301 // Other Algebra
302 //--------------------------------------------------------------
303 SHarmonic2D& SHarmonic2D::mpaxis(const valarray < complex <double> > & shmulti){
304  (*sh).multid1(shmulti);
305  return *this;
306 }
307 SHarmonic2D& SHarmonic2D::mxaxis(const valarray < complex <double> > & shmulti){
308  (*sh).multid2(shmulti);
309  return *this;
310 }
311 SHarmonic2D& SHarmonic2D::myaxis(const valarray < complex <double> > & shmulti){
312  (*sh).multid3(shmulti);
313  return *this;
314 }
315 //--------------------------------------------------------------
316 //--------------------------------------------------------------
317 // SHarmonic2D& SHarmonic2D::Dp(){
318 // //--------------------------------------------------------------
319 // // P-difference with derivative at #0 set to 0, and f at #np equal to #np-1
320 // //--------------------------------------------------------------
321 // Array2D< complex<double> > ma(numx(), numy());
322 // ma = 0.0;
323 
324 // // GSlice_iter< complex<double> > it1(p0(nump()-2)), it2(p0(nump()-1));
325 // // for(int i=0; i< numx()*numy(); ++i){
326 // // ma(i) = *it1; ma(i) -= *it2;
327 // // ++it1; ++it2;
328 // // }
329 
330 // // *sh = (*sh).Dd1();
331 
332 // // it1 = p0(0), it2 = p0(nump()-1);
333 // // for(int i=0; i< numx()*numy(); ++i){
334 // // *it1 = 0.0; *it2 = ma(i);
335 // // ++it1; ++it2;
336 // // }
337 // return *this;
338 // }
339 //--------------------------------------------------------------
340 // X-difference
342 
343  *sh = (*sh).Dd2(); // Worry about boundaries elsewhere
344  return *this;
345 }
346 // y-difference
348 
349  *sh = (*sh).Dd3(); // Worry about boundaries elsewhere
350  return *this;
351 }
352 SHarmonic2D& SHarmonic2D::mxy_matrix(Array2D< complex<double> >& shmultiM){
353  int st(0), nxt(nump());
354  for (int im(0); im < shmultiM.dim(); ++im) {
355  for (int ip(st); ip < nxt; ++ip)
356  (*sh)(ip) *= shmultiM(im);
357  st += nump(); nxt += nump();
358  }
359  return *this;
360 }
361 //--------------------------------------------------------------
362 
363 // Filter Pcells
365  *sh = (*sh).Filterd1(N);
366  return *this;
367 }
368 
369 //**************************************************************
370 
371 //**************************************************************
372 // Definition of the "Field1D" Class
373 //--------------------------------------------------------------
374 // Constructor and Destructor
375 //--------------------------------------------------------------
376 // Constructor
378  fi = new valarray<complex<double> >(numx);
379 }
380 // Copy constructor
382  fi = new valarray<complex<double> >(other.numx());
383  *fi = other.array();
384 }
385 // Destructor
387  delete fi;
388 }
389 
390 //--------------------------------------------------------------
391 // Operators
392 //--------------------------------------------------------------
393 // Copy assignment operator
394 Field1D& Field1D::operator=(const complex<double> & d){
395  *fi = d;
396  return *this;
397 }
398 Field1D& Field1D::operator=(const valarray<complex<double> >& other){
399  *fi = other;
400  return *this;
401 }
403  if (this != &other) { //self-assignment
404  *fi = other.array();
405  }
406  return *this;
407 }
408 // *=
409 Field1D& Field1D::operator*=(const complex<double> & d){
410  (*fi) *=d;
411  return *this;
412 }
413 Field1D& Field1D::operator*=(const valarray<complex<double> >& fimulti){
414  (*fi) *= fimulti;
415  return *this;
416 }
418  (*fi) *= fimulti.array();
419  return *this;
420 }
421 // +=
422 Field1D& Field1D::operator+=(const complex<double> & d){
423  (*fi) +=d;
424  return *this;
425 }
427  (*fi) += fiadd.array();
428  return *this;
429 }
430 // -=
431 Field1D& Field1D::operator-=(const complex<double> & d){
432  (*fi) -=d;
433  return *this;
434 }
436  (*fi) -= fimin.array();
437  return *this;
438 }
439 
440 //--------------------------------------------------------------
442 //--------------------------------------------------------------
443  for (int i(0); i < numx(); ++i) {
444  (*fi)[i] = (*fi)[i].real();
445  }
446  return *this;
447 }
448 
449 //--------------------------------------------------------------
451 //--------------------------------------------------------------
452  //--------------------------------------------------------//
453  //--------------------------------------------------------//
455  // valarray<complex<double> > df(numx());
456 
457  // df[0] = (*fi)[1]-(*fi)[0];
458  // df[1] = 1.0/12.0*((*fi)[4]-6.0*(*fi)[3]+18.0*(*fi)[2]-10.0*(*fi)[1]-3.0*(*fi)[0]);
459 
460  // for (long i(2); i < numx()-2; ++i) {
461  // df[i] = 1.0/12.0*(-(*fi)[i+2]+8.0*(*fi)[i+1]-8.0*(*fi)[i-1]+(*fi)[i-2]);
462  // }
463 
464  // df[numx()-2] = 1.0/12.0*(3.0*(*fi)[numx()-1]+10.0*(*fi)[numx()-2]-18.0*(*fi)[numx()-3]+6.0*(*fi)[numx()-4]-(*fi)[numx()-5]);
465  // df[numx()-1] = (*fi)[numx()-1]-(*fi)[numx()-2];
466 
467  // for (long i(0); i < numx(); ++i)
468  // (*fi)[i] = -2.0*df[i];
469  //--------------------------------------------------------//
470  //--------------------------------------------------------//
471  // 2nd order
472  // df[0] = 2.0*((*fi)[0]-(*fi)[1]);
473  // for(long i(0); i < long(numx())-1; ++i) {
474  // df[i] = (*fi)[i-1]-(*fi)[i+1];
475  // }
476  // df[numx()-1] = 2.0*((*fi)[numx()-2]-(*fi)[numx()-1]);
477  // *fi = df;
478 
479  for(long i(0); i< long(numx())-2; ++i) {
480  (*fi)[i] -= (*fi)[i+2];
481  }
482 
483  for(long i(numx()-3); i>-1; --i) {
484  (*fi)[i+1] = (*fi)[i];
485  }
486  //--------------------------------------------------------//
487  //--------------------------------------------------------//
488  return *this;
489 }
490 //--------------------------------------------------------------
491 //**************************************************************
492 
493 //**************************************************************
494 // Definition of the "Field2D" Class
495 //--------------------------------------------------------------
496 // Constructor and Destructor
497 //--------------------------------------------------------------
498 // Constructor
499 Field2D:: Field2D(size_t numx, size_t numy) {
500  fi = new Array2D < complex <double> >(numx,numy);
501 }
502 // Copy constructor
504  fi = new Array2D < complex < double > >(other.numx(),other.numy());
505  *fi = other.array();
506 }
507 // Destructor
509  delete fi;
510 }
511 
512 //--------------------------------------------------------------
513 // Operators
514 //--------------------------------------------------------------
515 // Copy assignment operator
516 Field2D& Field2D::operator=(const complex<double>& d){
517  *fi = d;
518  return *this;
519 }
521  if (this != &other) { //self-assignment
522  *fi = other.array();
523  }
524  return *this;
525 }
526 // *=
527 Field2D& Field2D::operator*=(const complex<double>& d){
528  (*fi) *=d;
529  return *this;
530 }
531 
533  (*fi) *= fimulti.array();
534  return *this;
535 }
536 // +=
537 Field2D& Field2D::operator+=(const complex<double>& d){
538  (*fi) +=d;
539  return *this;
540 }
542  (*fi) += fiadd.array();
543  return *this;
544 }
545 // -=
546 Field2D& Field2D::operator-=(const complex<double>& d){
547  (*fi) -=d;
548  return *this;
549 }
551  (*fi) -= fimin.array();
552  return *this;
553 }
554 
555 //--------------------------------------------------------------
557 //--------------------------------------------------------------
558  *fi = (*fi).Dd1();
559  return *this;
560 }
561 //--------------------------------------------------------------
563 //--------------------------------------------------------------
564  *fi = (*fi).Dd2();
565  return *this;
566 }
567 //--------------------------------------------------------------
568 //**************************************************************
569 
570 //**************************************************************
571 //**************************************************************
572 // Definition of the Electromagnetic Fields Class
573 //**************************************************************
574 //**************************************************************
575 
576 //**************************************************************
577 //--------------------------------------------------------------
578 // Constructor and Destructor for 1D
579 //--------------------------------------------------------------
580 // Constructor
581 EMF1D:: EMF1D(size_t nx) {
582  fie = new vector<Field1D> (6,Field1D(nx));
583 
584 }
585 // Copy constructor
586 EMF1D:: EMF1D(const EMF1D& other){
587  fie = new vector<Field1D>(6,Field1D(other(1).numx()));
588  for(int i=0; i < other.dim() ; ++i) (*fie)[i] = other(i);
589 }
590 // Destructor
592  delete fie;
593 }
594 //--------------------------------------------------------------
595 // Operators for 1D
596 //--------------------------------------------------------------
597 
598 // Copy assignment operator
599 EMF1D& EMF1D::operator=(const complex<double>& d){
600  for(int i=0; i < dim() ; ++i)
601  (*fie)[i] = d;
602  return *this;
603 }
605  for(int i=0; i < dim() ; ++i){
606  if (&((*fie)[i]) != &h) { //self-assignment
607  (*fie)[i] = h;
608  }
609  }
610  return *this;
611 }
612 EMF1D& EMF1D::operator=(const EMF1D& other){
613  if (this != &other) { //self-assignment
614  for(int i=0; i < dim() ; ++i)
615  (*fie)[i] = other(i);
616  }
617  return *this;
618 }
619 // *=
620 EMF1D& EMF1D::operator*=(const complex<double>& d){
621  for(int i=0; i < dim() ; ++i)
622  (*fie)[i] *= d;
623  return *this;
624 }
626  if (this != &other) { //self-assignment
627  for(int i=0; i < dim() ; ++i)
628  (*fie)[i] *= other(i);
629  }
630  return *this;
631 }
632 // +=
633 EMF1D& EMF1D::operator+=(const complex<double>& d){
634  for(int i=0; i < dim() ; ++i)
635  (*fie)[i] += d;
636  return *this;
637 }
639  if (this != &other) { //self-assignment
640  for(int i=0; i < dim() ; ++i)
641  (*fie)[i] += other(i);
642  }
643  return *this;
644 }
645 // -=
646 EMF1D& EMF1D::operator-=(const complex<double>& d){
647  for(int i=0; i < dim() ; ++i)
648  (*fie)[i] -= d;
649  return *this;
650 }
652  if (this != &other) { //self-assignment
653  for(int i=0; i < dim() ; ++i)
654  (*fie)[i] -= other(i);
655  }
656  return *this;
657 }
658 
659 //**************************************************************
660 //--------------------------------------------------------------
661 // Constructor and Destructor for 2D
662 //--------------------------------------------------------------
663 // Constructor
664 EMF2D:: EMF2D(size_t nx, size_t ny) {
665  fie = new vector<Field2D> (6,Field2D(nx,ny));
666 
667 }
668 // Copy constructor
669 EMF2D:: EMF2D(const EMF2D& other){
670  fie = new vector<Field2D>(6,Field2D(other(1).numx(),other(1).numy()));
671  for(int i=0; i < other.dim() ; ++i) (*fie)[i] = other(i);
672 }
673 // Destructor
675  delete fie;
676 }
677 //--------------------------------------------------------------
678 // Operators for 2D
679 //--------------------------------------------------------------
680 
681 // Copy assignment operator
682 EMF2D& EMF2D::operator=(const complex<double>& d){
683  for(int i=0; i < dim() ; ++i)
684  (*fie)[i] = d;
685  return *this;
686 }
688  for(int i=0; i < dim() ; ++i){
689  if (&((*fie)[i]) != &h) { //self-assignment
690  (*fie)[i] = h;
691  }
692  }
693  return *this;
694 }
695 EMF2D& EMF2D::operator=(const EMF2D& other){
696  if (this != &other) { //self-assignment
697  for(int i=0; i < dim() ; ++i)
698  (*fie)[i] = other(i);
699  }
700  return *this;
701 }
702 // *=
703 EMF2D& EMF2D::operator*=(const complex<double>& d){
704  for(int i=0; i < dim() ; ++i)
705  (*fie)[i] *= d;
706  return *this;
707 }
709  if (this != &other) { //self-assignment
710  for(int i=0; i < dim() ; ++i)
711  (*fie)[i] *= other(i);
712  }
713  return *this;
714 }
715 // +=
716 EMF2D& EMF2D::operator+=(const complex<double>& d){
717  for(int i=0; i < dim() ; ++i)
718  (*fie)[i] += d;
719  return *this;
720 }
722  if (this != &other) { //self-assignment
723  for(int i=0; i < dim() ; ++i)
724  (*fie)[i] += other(i);
725  }
726  return *this;
727 }
728 // -=
729 EMF2D& EMF2D::operator-=(const complex<double>& d){
730  for(int i=0; i < dim() ; ++i)
731  (*fie)[i] -= d;
732  return *this;
733 }
735  if (this != &other) { //self-assignment
736  for(int i=0; i < dim() ; ++i)
737  (*fie)[i] -= other(i);
738  }
739  return *this;
740 }
741 
742 
743 //**************************************************************
744 // Definition of the 1D distribution function
745 //--------------------------------------------------------------
746 // Constructors and Destructor
747 //--------------------------------------------------------------
748 // Constructor
749 DistFunc1D:: DistFunc1D(size_t l, size_t m, size_t np, double pma, size_t nx, double q=1, double _ma=1)
750  : lmax(l), mmax(m), pmx(pma), charge(q), ma(_ma), ind(l+1,m+1) {
751 
752 // Initialize the array of the harmonics
753  if (lmax < 1) {
754  cout << "l0 < 1 is not acceptable.\n";
755  exit(1);
756  }
757 
758 // Generate container for the harmonics
759  sz = ((mmax+1)*(2*lmax-mmax+2))/2;
760  df = new vector<SHarmonic1D>(sz,SHarmonic1D(np,nx));
761  valarray<int> filter_ceiling(0,sz);
762 // Define the index for the triangular array
763  ind = -1;
764 
765  if (mmax == 0)
766  {
767  for(int il(0); il < lmax+1 ; ++il){
768  ind(il,0) = il;
769 
770  // filter_ceiling[il] = floor(il/ceil(lmax/np));
771  filter_ceiling[il] = ((il < np)?il:np);
772  }
773 
774  }
775  else
776  {
777  for(int il=0; il < lmax+1 ; ++il){
778  for(int im=0; im < ((mmax < il)? mmax:il)+1; ++im){
779  ind(il,im) = ((il < mmax+1)?((il*(il+1))/2+im):
780  (il*(mmax+1)-(mmax*(mmax+1))/2 + im));
781  filter_ceiling[ind(il,im)] = ((il < np)?il:np);
782  }
783  }
784  }
785  // exit(1);
786 
787 }
788 //- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
789 
790 // Copy constructor
792  : lmax(other.l0()), mmax(other.m0()), pmx(other.pmax()),
793  charge(other.q()), ma(other.mass()), ind(other.l0()+1,other.m0()+1),
794  filter_ceiling(((mmax+1)*(2*lmax-mmax+2))/2) {
795 
796 // Generate container for the harmonics
797  sz = ((mmax+1)*(2*lmax-mmax+2))/2;
798  df = new vector<SHarmonic1D>(sz,SHarmonic1D(other(0).nump(),other(0).numx()));
799 
800 
801  for(size_t i(0); i < sz ; ++i){
802  (*df).push_back(other(i));
803  }
804 
805 // Define the index for the triangular array
806  ind = -1;
807  if (mmax == 0)
808  {
809  for(int il(0); il < lmax+1 ; ++il){
810  ind(il,0) = il;
811  filter_ceiling[il] = (il < other(0).nump())?il:other(0).nump();
812  }
813 
814  }
815  else
816  {
817  for(int il=0; il < lmax+1 ; ++il){
818  for(int im=0; im < ((mmax < il)? mmax:il)+1; ++im){
819  ind(il,im) = ((il < mmax+1)?((il*(il+1))/2+im):
820  (il*(mmax+1)-(mmax*(mmax+1))/2 + im));
821  filter_ceiling[ind(il,im)] = (il*im < other(0).nump())?il*im:other(0).nump();
822  }
823  }
824  }
825  // exit(1);
826 
827 }
828 //- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
829 
830 // Destructor
832  delete df;
833 }
834 //--------------------------------------------------------------
835 // Access
836 //--------------------------------------------------------------
837 // Pointer to the l-th harmonic
839 // if ((l < 0) || (l> lmax)) return NULL;
840  return (*df)[size_t(i)];
841 }
842 
844 // if ((l < 0) || (l> lmax)) return NULL;
845  return (*df)[size_t(i)];
846 }
847 
848 SHarmonic1D& DistFunc1D::operator()(size_t l, size_t m) {
849 // if ((l < 0) || (l> lmax)) return NULL;
850  return (*df)[ind(l,m)];
851 }
852 
853 SHarmonic1D& DistFunc1D::operator()(size_t l, size_t m) const {
854 // if ((l < 0) || (l> lmax)) return NULL;
855  return (*df)[ind(l,m)];
856 }
857 
858 // Pointer to the "n" neighbor of the l harmonic
859 // SHarmonic1D* DistFunc1D::Compus(size_t l, _Compus1D n) const {
860 // return _Neighbors[2*l+n];
861 // }
862 //--------------------------------------------------------------
863 // Operators
864 //--------------------------------------------------------------
865 // Copy assignment operator
866 DistFunc1D& DistFunc1D::operator=(const complex<double> & d){
867  for(size_t i(0); i < dim() ; ++i){
868  (*df)[i] = d;
869  }
870  return *this;
871 }
873  for(size_t i(0); i < dim() ; ++i){
874  if (&((*df)[i]) != &h) { //self-assignment
875  (*df)[i] = h;
876  }
877  }
878  return *this;
879 }
881  if (this != &other) { //self-assignment
882  for(size_t i(0); i < dim() ; ++i) {
883  (*df)[i] = other(i);
884  }
885  }
886  return *this;
887 }
888 // *=
889 DistFunc1D& DistFunc1D::operator*=(const complex<double> & d){
890  for(size_t i(0); i < dim() ; ++i) {
891  (*df)[i] *= d;
892  }
893  return *this;
894 }
896  if (this != &other) { //self-assignment
897  for(size_t i(0); i < dim() ; ++i) {
898  (*df)[i] *= other(i);
899  }
900  }
901  return *this;
902 }
903 // +=
904 DistFunc1D& DistFunc1D::operator+=(const complex<double> & d){
905  for(size_t i(0); i < dim() ; ++i) {
906  (*df)[i] += d;
907  }
908  return *this;
909 }
911  if (this != &other) { //self-assignment
912  for(size_t i(0); i < dim() ; ++i) {
913  (*df)[i] += other(i);
914  }
915  }
916  return *this;
917 }
918 // -=
919 DistFunc1D& DistFunc1D::operator-=(const complex<double> & d){
920  for(size_t i(0); i < dim() ; ++i) {
921  (*df)[i] -= d;
922  }
923  return *this;
924 }
926  if (this != &other) { //self-assignment
927  for(size_t i(0); i < dim() ; ++i) {
928  (*df)[i] -= other(i);
929  }
930  }
931  return *this;
932 }
933 
935  for(size_t i(0); i < dim() ; ++i) {
936  (*df)[i].Filterp(i);
937  // (*df)[i].Filterp(filter_ceiling[i]);
938  }
939  return *this;
940 }
941 //--------------------------------------------------------------------------------------------------------------------------
942 // Moments for Hydro
943 //--------------------------------------------------------------------------------------------------------------------------
944 //--------------------------------------------------------------------------------------------------------------------------
945 valarray<double> DistFunc1D::getdensity(){
946 
947  valarray<double> out((*df)[0].numx());
948 // valarray<complex<double> > vr(Algorithms::MakeAxis(
949 // static_cast<complex<double> > (pmax()/(2.0*((*df)[0].nump())-1.0)),static_cast<complex<double> >(pmax()),(*df)[0].nump()
950 // ));
951 
952  valarray<complex<double> > vr(Algorithms::MakeCAxis(
953  static_cast<complex<double> > (0.0),static_cast<complex<double> >(pmax()),(*df)[0].nump()
954  ));
955 
956  for (size_t i(0); i<(*df)[0].numx();++i){
957  out[i] = (4.0*M_PI*Algorithms::moment((*df)[0].xVec(i),vr,2.0)).real();
958  }
959 
960  return out;
961 }
962 
963 //--------------------------------------------------------------------------------------------------------------------------
964 //--------------------------------------------------------------------------------------------------------------------------
965 valarray<double> DistFunc1D::getcurrent(size_t dir){
966  // complex<double> ii(0.0,-1.0);
967  valarray<double> out((*df)[0].numx());
968 
969  // valarray<complex<double> > vr(Algorithms::MakeAxis(
970  // static_cast<complex<double> > (pmax()/(2.0*((*df)[0].nump()))),static_cast<complex<double> >(pmax()),(*df)[0].nump()
971  // ));
972 
973  valarray<complex<double> > vr(Algorithms::MakeCAxis(
974  static_cast<complex<double> > (0.0),static_cast<complex<double> >(pmax()),(*df)[0].nump()
975  ));
976 
977 
978  if (dir == 0)
979  {
980  for (size_t i(0); i<(*df)[0].numx();++i){
981  out[i] = (4.0/3.0*M_PI*charge/ma)*(Algorithms::relativistic_invg_moment((*df)[1].xVec(i),vr,3.0)).real();
982  }
983  }
984  else if (dir == 1)
985  {
986  for (size_t i(0); i<(*df)[0].numx();++i){
987  out[i] = (8.0/3.0*M_PI*charge/ma)*(Algorithms::relativistic_invg_moment((*df)[2].xVec(i),vr,3.0)).real();
988  }
989  }
990  else if (dir == 2)
991  {
992  for (size_t i(0); i<(*df)[0].numx();++i){
993  out[i] = (-8.0/3.0*M_PI*charge/ma)*(Algorithms::relativistic_invg_moment((*df)[2].xVec(i),vr,3.0)).imag();
994  }
995  }
996 
997  else
998  {
999  std::cout << "\n\n ERROR: Wrong current Direction \n\n ";
1000  exit(1);
1001  }
1002 
1003  return out;
1004 
1005 
1006 }
1007 //--------------------------------------------------------------------------------------------------------------------------
1008 valarray<double> DistFunc1D::getcurrent(size_t dir) const{
1009  // complex<double> ii(0.0,-1.0);
1010  valarray<double> out((*df)[0].numx());
1011  // valarray<complex<double> > vr(Algorithms::MakeAxis(
1012  // static_cast<complex<double> > (pmax()/(2.0*((*df)[0].nump()))),static_cast<complex<double> >(pmax()),(*df)[0].nump()
1013  // ));
1014 
1015  valarray<complex<double> > vr(Algorithms::MakeCAxis(
1016  static_cast<complex<double> > (0.0),static_cast<complex<double> >(pmax()),(*df)[0].nump()
1017  ));
1018 
1019 
1020  if (dir == 0)
1021  {
1022  for (size_t i(0); i<(*df)[0].numx();++i){
1023  out[i] = (4.0/3.0*M_PI*charge/ma)*(Algorithms::relativistic_invg_moment((*df)[1].xVec(i),vr,3.0)).real();
1024  }
1025  }
1026  else if (dir == 1)
1027  {
1028  for (size_t i(0); i<(*df)[0].numx();++i){
1029  out[i] = (8.0/3.0*M_PI*charge/ma)*(Algorithms::relativistic_invg_moment((*df)[2].xVec(i),vr,3.0)).real();
1030  }
1031  }
1032  else if (dir == 2)
1033  {
1034  for (size_t i(0); i<(*df)[0].numx();++i){
1035  out[i] = (-8.0/3.0*M_PI*charge/ma)*(Algorithms::relativistic_invg_moment((*df)[2].xVec(i),vr,3.0)).imag();
1036  }
1037  }
1038 
1039  else
1040  {
1041  std::cout << "\n\n ERROR: Wrong current Direction \n\n ";
1042  exit(1);
1043  }
1044 
1045  return out;
1046 
1047 
1048 }
1049 //--------------------------------------------------------------------------------------------------------------------------
1051  // complex<double> ii(0.0,-1.0);
1052  Array2D<double> out(3,(*df)[0].numx());
1053 // valarray<complex<double> > vr(Algorithms::MakeAxis(
1054 // static_cast<complex<double> > (pmax()/(2.0*((*df)[0].nump())-1.0)),static_cast<complex<double> >(pmax()),(*df)[0].nump()
1055 // ));
1056 
1057  valarray<complex<double> > vr(Algorithms::MakeCAxis(
1058  static_cast<complex<double> > (0.0),static_cast<complex<double> >(pmax()),(*df)[0].nump()
1059  ));
1060 
1061  double current_c1(4.0/3.0*M_PI*charge/ma);
1062  double current_c2(2.0*current_c1);
1063  double current_c3(-1.0*current_c2);
1064 
1065  for (size_t i(0); i<(*df)[0].numx();++i){
1066  out(0,i) = (current_c1)*(Algorithms::relativistic_invg_moment((*df)[1].xVec(i),vr,3.0)).real();
1067 
1068  out(1,i) = (current_c2)*(Algorithms::relativistic_invg_moment((*df)[2].xVec(i),vr,3.0)).real();
1069 
1070  out(2,i) = (current_c3)*(Algorithms::relativistic_invg_moment((*df)[2].xVec(i),vr,3.0)).imag();
1071 
1072  }
1073 
1074  return out;
1075 
1076 
1077 }
1078 //--------------------------------------------------------------------------------------------------------------------------
1079 //--------------------------------------------------------------------------------------------------------------------------
1080 // Moments for Hydro
1081 valarray<double> DistFunc1D::getpressure(){
1082 
1083  valarray<double> out((*df)[0].numx());
1084 // valarray<complex<double> > vr(Algorithms::MakeAxis(
1085 // static_cast<complex<double> > (pmax()/(2.0*((*df)[0].nump())-1.0)),static_cast<complex<double> >(pmax()),(*df)[0].nump()
1086 // ));
1087 
1088  valarray<complex<double> > vr(Algorithms::MakeCAxis(
1089  static_cast<complex<double> > (0.0),static_cast<complex<double> >(pmax()),(*df)[0].nump()
1090  ));
1091 
1092  for (size_t i(0); i<(*df)[0].numx();++i){
1093  out[i] = (4.0/3.0/ma*M_PI*Algorithms::moment((*df)[0].xVec(i),vr,4.0)).real();
1094  }
1095 
1096  return out;
1097 }
1098 
1099 //--------------------------------------------------------------------------------------------------------------------------
1100 //--------------------------------------------------------------------------------------------------------------------------
1101 // Debug
1102 
1104 
1105  for (int indx(0); indx<dim();++indx){
1106  for (size_t i(0); i<(*df)[indx].numx();++i){
1107  for (size_t p(0); p<(*df)[indx].nump();++p){
1108  if ( isnan((*df)[indx](p,i).real()) || isnan((*df)[indx](p,i).imag()) )
1109  {
1110  std::cout << "NaN @ (" << indx << "," << p << "," << i << ")\n";
1111  exit(1);
1112  }
1113  }
1114  }
1115  }
1116 // std::cout << "OK! \n";
1117  return;
1118 
1119 
1120 }
1121 
1122 //--------------------------------------------------------------------------------------------------------------------------
1123 //*********************************************************************************************************************
1124 
1125 //*********************************************************************************************************************
1126 // Definition of the 2D distribution function
1127 //--------------------------------------------------------------
1128 // Constructors and Destructor
1129 //--------------------------------------------------------------
1130 // Constructor
1131 DistFunc2D:: DistFunc2D(size_t l, size_t m, size_t np, size_t nx, size_t ny, double q=1, double _ma=1)
1132  : lmax(l), mmax(m), charge(q), ma(_ma), ind(l+1,m+1) {
1133  // double q=1, double _ma=1)
1134 
1135 // Initialize the array of the harmonics
1136  if (lmax < 1 || mmax < 1) {
1137  cout << "l0 < 1 or m0 < 1 is not acceptable.\n";
1138  exit(1);
1139  }
1140 
1141  sz = ((mmax+1)*(2*lmax-mmax+2))/2;
1142 
1143 // Generate container for the harmonics
1144  df = new vector<SHarmonic2D>(sz,SHarmonic2D(np,nx,ny));
1145 
1146 // Define the index for the triangular array
1147  ind = -1;
1148  for(int il=0; il < lmax+1 ; ++il){
1149  for(int im=0; im < ((mmax < il)? mmax:il)+1; ++im){
1150  ind(il,im) = ((il < mmax+1)?((il*(il+1))/2+im):
1151  (il*(mmax+1)-(mmax*(mmax+1))/2 + im));
1152  }
1153  }
1154 
1155 }
1156 //- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
1157 
1158 // Copy constructor
1160  : lmax(other.l0()), mmax(other.m0()), charge(other.q()), ma(other.mass()), ind(other.ldim(),other.mdim()) {
1161 
1162 // Generate container for the harmonics
1163  df = new vector<SHarmonic2D>;
1164  for(size_t l(0); l < other.l0()+1 ; ++l){
1165  for(size_t m(0); m < other.m0()+1 ; ++m){
1166  (*df).push_back(*(other(l,m)));
1167  }
1168  }
1169 
1170  // Define the index for the triangular array
1171  ind = -1;
1172  for(int il=0; il < l0()+1 ; ++il){
1173  for(int im=0; im < ((m0() < il)? m0():il)+1; ++im){
1174  ind(il,im) = ((il < m0()+1)?((il*(il+1))/2+im):
1175  (il*(m0()+1)-(m0()*(m0()+1))/2 + im));
1176  }
1177  }
1178 
1179 }
1180 //- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
1181 
1182 // Destructor
1184  delete df;
1185 }
1186 //--------------------------------------------------------------
1187 // Access THESE WERE CHANGED IS BE (L,M) RATHER THAN (I)... WHY?
1188 //--------------------------------------------------------------
1190 
1191 // SHarmonic2D* DistFunc2D::operator()(int l, int m) {
1192 // if ((l < 0) || (l> lmax) || (m < 0) || (m> mmax)) return NULL;
1193 // return &((*df)[size_t(l*(mmax+1)+m)]);
1194 
1195 // Pointer to the l-th harmonic
1197 
1198  return &((*df)[size_t(i)]);
1199 }
1200 
1201 // SHarmonic2D* DistFunc2D::operator()(int l, int m) const {
1202 // if ((l < 0) || (l> lmax) || (m < 0) || (m> mmax)) return NULL;
1203 //
1204 // return &((*df)[size_t(l*(mmax+1)+m)]);
1205 
1207  // if ((l < 0) || (l> lmax) || (m < 0) || (m > mmax)) return NULL;
1208  return &((*df)[size_t(i)]);
1209 }
1210 
1211 // // Pointer to the "n" neighbor of the l harmonic
1212 // SHarmonic1D* DistFunc2D::Compus(size_t l, _Compus1D n) const {
1213 // return _Neighbors[2*l+n];
1214 // }
1215 //--------------------------------------------------------------
1216 // Operators
1217 //--------------------------------------------------------------
1218 // Copy assignment operator
1219 DistFunc2D& DistFunc2D::operator=(const complex <double>& d){
1220  for(size_t i(0); i < dim() ; ++i){
1221  (*df)[i] = d;
1222  }
1223  return *this;
1224 }
1226  for(size_t i(0); i < dim() ; ++i){
1227  if (&((*df)[i]) != &h) { //self-assignment
1228  (*df)[i] = h;
1229  }
1230  }
1231  return *this;
1232 }
1234  if (this != &other) { //self-assignment
1235  // for(size_t i(0); i < dim() ; ++i) {
1236  size_t i(0);
1237  for(size_t l(0); l < ldim() ; ++l)
1238  {
1239  for(size_t m(0); m < mdim() ; ++m)
1240  {
1241  (*df)[i] = *(other(l,m));
1242  ++i;
1243  }
1244  }
1245  }
1246  return *this;
1247 }
1248 // *=
1249 DistFunc2D& DistFunc2D::operator*=(const complex <double>& d){
1250  for(size_t i(0); i < dim() ; ++i) {
1251  (*df)[i] *= d;
1252  }
1253  return *this;
1254 }
1256  if (this != &other) { //self-assignment
1257  // for(size_t i(0); i < dim() ; ++i) {
1258  size_t i(0);
1259  for(size_t l(0); l < ldim() ; ++l)
1260  {
1261  for(size_t m(0); m < mdim() ; ++m)
1262  {
1263  (*df)[i] *= *(other(l,m));
1264  ++i;
1265  }
1266  }
1267  }
1268  return *this;
1269 }
1270 // +=
1271 DistFunc2D& DistFunc2D::operator+=(const complex <double>& d){
1272  for(size_t i(0); i < dim() ; ++i) {
1273  (*df)[i] += d;
1274  }
1275  return *this;
1276 }
1278 // MORE L AND M STUFF TO CHECK AGAINST ORIGINAL
1279 // if (this != &other) //self-assignment
1280 // {
1281 // size_t i(0);
1282 // // for(size_t i(0); i < dim() ; ++i) {
1283 // for(size_t l(0); l < ldim() ; ++l)
1284 // {
1285 // for(size_t m(0); m < mdim() ; ++m)
1286 // {
1287 // (*df)[i] *= *(other(l,m));
1288 // ++i;
1289 // }
1290  if (this != &other) { //self-assignment
1291  for(size_t i(0); i < dim() ; ++i) {
1292  (*df)[i] += *(other(i));
1293  }
1294  }
1295  return *this;
1296 }
1297 // -=
1298 DistFunc2D& DistFunc2D::operator-=(const complex <double>& d){
1299  for(size_t i(0); i < dim() ; ++i) {
1300  (*df)[i] -= d;
1301  }
1302  return *this;
1303 }
1305  if (this != &other) { //self-assignment
1306 // MORE L AND M STUFF TO CHECK AGAINST ORIGINAL
1307 // // for(size_t i(0); i < dim() ; ++i) {
1308 // size_t i(0);
1309 // for(size_t l(0); l < ldim() ; ++l)
1310 // {
1311 // for(size_t m(0); m < mdim() ; ++m)
1312 // {
1313 // (*df)[i] *= *(other(l,m));
1314 // ++i;
1315 // }
1316  for(size_t i(0); i < dim() ; ++i) {
1317  (*df)[i] -= *(other(i));
1318  }
1319  }
1320  return *this;
1321 }
1322 
1323 // DistFunc2D& DistFunc2D::Filterp(){
1324 // for(size_t i(0); i < dim() ; ++i) {
1325 // (*df)[i].Filterp(i);
1326 // }
1327 // return *this;
1328 // }
1329 //--------------------------------------------------------------
1330 //**************************************************************
1331 //**************************************************************
1332 // Definition of the "Field1D" Class
1333 //--------------------------------------------------------------
1334 // Constructor and Destructor
1335 //--------------------------------------------------------------
1336 // Constructor
1337 Hydro1D:: Hydro1D(size_t nx, double _mass, double _charge): hydromass(_mass), hydrocharge(_charge) {
1338  hn = new valarray<double >(nx);
1339  hvx = new valarray<double >(nx);
1340  hvy = new valarray<double >(nx);
1341  hvz = new valarray<double >(nx);
1342  ht = new valarray<double >(nx);
1343  hz = new valarray<double >(nx);
1344 }
1345 // Copy constructor
1347  hn = new valarray<double >(other.numx());
1348  *hn = other.densityarray();
1349 
1350  hvx = new valarray<double >(other.numx());
1351  *hvx = other.vxarray();
1352 
1353  hvy = new valarray<double >(other.numx());
1354  *hvy = other.vyarray();
1355 
1356  hvz = new valarray<double >(other.numx());
1357  *hvz = other.vzarray();
1358 
1359  ht = new valarray<double >(other.numx());
1360  *ht = other.temperaturearray();
1361 
1362  hz = new valarray<double >(other.numx());
1363  *hz = other.Zarray();
1364 
1365 }
1366 // Destructor
1368  delete hn;
1369  delete hvx;
1370  delete hvy;
1371  delete hvz;
1372  delete ht;
1373  delete hz;
1374 }
1375 
1376 // Copy assignment operator
1377 Hydro1D& Hydro1D::operator=(const double & d){
1378  *hn = d;
1379  *hvx = d;
1380  *hvy = d;
1381  *hvz = d;
1382  *ht = d;
1383  *hz = d;
1384  return *this;
1385 }
1386 Hydro1D& Hydro1D::operator=(const valarray<double >& other){
1387  *hn = other;
1388  *hvx = other;
1389  *hvy = other;
1390  *hvz = other;
1391  *ht = other;
1392  *hz = other;
1393  return *this;
1394 }
1396 
1397  if (this != &other) { //self-assignment
1398  *hn = other.densityarray();
1399  *hvx = other.vxarray();
1400  *hvy = other.vyarray();
1401  *hvz = other.vzarray();
1402  *ht = other.temperaturearray();
1403  *hz = other.Zarray();
1404  }
1405  return *this;
1406 }
1407 
1408 // Copy assignment operator
1409 Hydro1D& Hydro1D::operator*=(const double & d){
1410  *hn *= d;
1411  *hvx *= d;
1412  *hvy *= d;
1413  *hvz *= d;
1414  *ht *= d;
1415  *hz *= d;
1416  return *this;
1417 }
1418 Hydro1D& Hydro1D::operator*=(const valarray<double >& other){
1419  *hn *= other;
1420  *hvx *= other;
1421  *hvy *= other;
1422  *hvz *= other;
1423  *ht *= other;
1424  *hz *= other;
1425  return *this;
1426 }
1428  if (this != &other) { //self-assignment
1429  *hn *= other.densityarray();
1430  *hvx *= other.vxarray();
1431  *hvy *= other.vyarray();
1432  *hvz *= other.vzarray();
1433  *ht *= other.temperaturearray();
1434  *hz *= other.Zarray();
1435 
1436  }
1437  return *this;
1438 }
1439 
1440 // Copy assignment operator
1441 Hydro1D& Hydro1D::operator+=(const double & d){
1442  *hn += d;
1443  *hvx += d;
1444  *hvy += d;
1445  *hvz += d;
1446  *ht += d;
1447  *hz += d;
1448 
1449  return *this;
1450 }
1451 Hydro1D& Hydro1D::operator+=(const valarray<double >& other){
1452  *hn += other;
1453  *hvx += other;
1454  *hvy += other;
1455  *hvz += other;
1456  *ht += other;
1457  *hz += other;
1458  return *this;
1459 }
1461  if (this != &other) { //self-assignment
1462  *hn += other.densityarray();
1463  *hvx += other.vxarray();
1464  *hvy += other.vyarray();
1465  *hvz += other.vzarray();
1466  *ht += other.temperaturearray();
1467  *hz += other.Zarray();
1468 
1469  }
1470  return *this;
1471 }
1472 
1473 // Copy assignment operator
1474 Hydro1D& Hydro1D::operator-=(const double & d){
1475  *hn -= d;
1476  *hvx -= d;
1477  *hvy -= d;
1478  *hvz -= d;
1479  *ht -= d;
1480  *hz -= d;
1481  return *this;
1482 }
1483 Hydro1D& Hydro1D::operator-=(const valarray<double >& other){
1484  *hn -= other;
1485  *hvx -= other;
1486  *hvy -= other;
1487  *hvz -= other;
1488  *ht -= other;
1489  *hz -= other;
1490 
1491  return *this;
1492 }
1494  if (this != &other) { //self-assignment
1495  *hn -= other.densityarray();
1496  *hvx -= other.vxarray();
1497  *hvy -= other.vyarray();
1498  *hvz -= other.vzarray();
1499  *ht -= other.temperaturearray();
1500  *hz -= other.Zarray();
1501 
1502  }
1503  return *this;
1504 }
1505 
1506 //**************************************************************
1507 // State for 1D electrostatic code
1508 //--------------------------------------------------------------
1509 // Constructor and Destructor
1510 //--------------------------------------------------------------
1511 // Constructor
1512 State1D:: State1D( size_t nx, vector<size_t> l0, vector<size_t> m0,
1513  vector<size_t> np, vector<double> pmax, vector<double> q, vector<double> ma,
1514  double _hydromass, double _hydrocharge)
1515  : ns(l0.size()) {
1516  if (ns != np.size()) {
1517  cout << "ERROR:Overdetermined number of species\n";
1518  exit(1);
1519  }
1520  sp = new vector<DistFunc1D>;
1521  for(size_t s(0); s < ns; ++s){
1522  (*sp).push_back(DistFunc1D(l0[s],m0[s],np[s],pmax[s],nx,q[s],ma[s]));
1523  }
1524  flds = new EMF1D(nx);
1525 
1526  hydro = new Hydro1D(nx,_hydromass,_hydrocharge);
1527 
1528 }
1529 
1530 // Copy constructor
1532  : ns(other.Species()) {
1533  sp = new vector<DistFunc1D>;
1534  for(size_t s(0); s < ns; ++s){
1535  (*sp).push_back(DistFunc1D(other.DF(s)));
1536  }
1537  flds = new EMF1D(other.FLD(0).numx());
1538  *flds = other.EMF();
1539 
1540  hydro = new Hydro1D(other.FLD(0).numx(),other.HYDRO().mass(),other.HYDRO().charge());
1541  *hydro = other.HYDRO();
1542 }
1543 
1544 // Destructor
1546  delete sp;
1547  delete flds;
1548  delete hydro;
1549 }
1550 //--------------------------------------------------------------
1551 // Operators
1552 //--------------------------------------------------------------
1553 // Copy assignment operator
1555  if (this != &other) { //self-assignment
1556  ns = other.Species();
1557  for(size_t s(0); s < ns; ++s){
1558  (*sp)[s] = other.DF(s);
1559  }
1560  *flds = other.EMF();
1561  *hydro = other.HYDRO();
1562 
1563  }
1564  return *this;
1565 }
1566 // =
1567 State1D& State1D::operator=(const complex<double> & d){
1568  for(size_t s(0); s < ns; ++s){
1569  (*sp)[s] = d;
1570  }
1571  *flds = d;
1572  *hydro = d.real();
1573  return *this;
1574 }
1575 // *=
1577  for(size_t s(0); s < ns; ++s){
1578  (*sp)[s] *= other.DF(s);
1579  }
1580  *flds *= other.EMF();
1581  *hydro *= other.HYDRO();
1582  return *this;
1583 }
1584 // *=
1585 State1D& State1D::operator*=(const complex<double> & d){
1586  for(size_t s(0); s < ns; ++s){
1587  (*sp)[s] *= d;
1588  }
1589  (*flds) *= d;
1590  *hydro *= d.real();
1591  return *this;
1592 }
1593 // +=
1595  for(size_t s(0); s < ns; ++s){
1596  (*sp)[s] += other.DF(s);
1597  }
1598  *flds += other.EMF();
1599  *hydro += other.HYDRO();
1600  return *this;
1601 }
1602 // +=
1603 State1D& State1D::operator+=(const complex<double> & d){
1604  for(size_t s(0); s < ns; ++s){
1605  (*sp)[s] += d;
1606  }
1607  (*flds) += d;
1608  *hydro += d.real();
1609  return *this;
1610 }
1611 // +=
1613  for(size_t s(0); s < ns; ++s){
1614  (*sp)[s] -= other.DF(s);
1615  }
1616  *flds -= other.EMF();
1617  *hydro -= other.HYDRO();
1618  return *this;
1619 }
1620 // +=
1621 State1D& State1D::operator-=(const complex<double> & d){
1622  for(size_t s(0); s < ns; ++s){
1623  (*sp)[s] -= d;
1624  }
1625  (*flds) -= d;
1626  *hydro -= d.real();
1627  return *this;
1628 }
1629 // // Debug
1631 
1632  for(size_t s(0); s < ns; ++s){
1633  (*sp)[s].checknan();
1634  }
1635 // std::cout << "Y OK! \n";
1636  return;
1637 }
1638 
1639 
1640 //--------------------------------------------------------------
1641 //**************************************************************
1642 
1643 //**************************************************************
1644 //**************************************************************
1645 // Definition of the State2D Class
1646 //**************************************************************
1647 //**************************************************************
1648 
1649 //**************************************************************
1650 //--------------------------------------------------------------
1651 // Constructor and Destructor
1652 //--------------------------------------------------------------
1653 // Constructor
1654 State2D:: State2D(size_t nx, size_t ny, vector<size_t> l0, vector<size_t> m0, vector<size_t> np, vector<double> q, vector<double> ma)
1655  : ns(l0.size()) {
1656  if (ns != np.size()) {
1657  cout << "ERROR:Overdetermined number of species\n";
1658  exit(1);
1659  }
1660  sp = new vector<DistFunc2D>;
1661  for(size_t s(0); s < ns; ++s){
1662  (*sp).push_back(DistFunc2D(l0[s],m0[s],np[s],nx,ny,q[s],ma[s]));
1663  }
1664  flds = new EMF2D(nx,ny);
1665 
1666 }
1667 
1668 // Copy constructor
1670  sp = new vector<DistFunc2D>;
1671  for(size_t s(0); s < ns; ++s){
1672  (*sp).push_back(DistFunc2D(other.DF(s).l0(),other.DF(s).m0(),
1673  other.DF(s)(0,0)->nump(),other.FLD(0).numx(),other.FLD(0).numy(),
1674  other.DF(s).q(),other.DF(s).mass()));
1675  }
1676  flds = new EMF2D(other.FLD(0).numx(),other.FLD(0).numy());
1677  *flds = other.EMF();
1678 }
1679 
1680 // Destructor
1682  delete sp;
1683  delete flds;
1684 }
1685 //--------------------------------------------------------------
1686 // Operators
1687 //--------------------------------------------------------------
1688 // Copy assignment operator
1690  if (this != &other) { //self-assignment
1691  for(size_t s(0); s < ns; ++s){
1692  (*sp).push_back(other.DF(s));
1693  }
1694  *flds = other.EMF();
1695  }
1696  return *this;
1697 }
1698 // =
1699 State2D& State2D::operator=(const complex<double>& d){
1700  for(size_t s(0); s < ns; ++s) (*sp)[s] = d;
1701  *flds = d;
1702  return *this;
1703 }
1704 // *=
1706  for(size_t s(0); s < ns; ++s) (*sp)[s] *= other.DF(s);
1707  *flds *= other.EMF();
1708  return *this;
1709 }
1710 // *=
1711 State2D& State2D::operator*=(const complex<double>& d){
1712  for(size_t s(0); s < ns; ++s) (*sp)[s] *= d;
1713  *flds *= d;
1714  return *this;
1715 }
1716 // +=
1718  for(size_t s(0); s < ns; ++s) (*sp)[s] += other.DF(s);
1719  *flds += other.EMF();
1720  return *this;
1721 }
1722 // +=
1723 State2D& State2D::operator+=(const complex<double>& d){
1724  for(size_t s(0); s < ns; ++s) (*sp)[s] += d;
1725  *flds += d;
1726  return *this;
1727 }
1728 // -=
1730  for(size_t s(0); s < ns; ++s) (*sp)[s] -= other.DF(s);
1731  *flds -= other.EMF();
1732  return *this;
1733 }
1734 // -=
1735 State2D& State2D::operator-=(const complex<double>& d){
1736  for(size_t s(0); s < ns; ++s) (*sp)[s] -= d;
1737  *flds -= d;
1738  return *this;
1739 }
1740 //--------------------------------------------------------------
1741 //--------------------------------------------------------------
1742 //--------------------------------------------------------------
1743 //**************************************************************
EMF2D & operator=(const complex< double > &d)
Definition: state.cpp:682
double charge
Definition: state.h:382
Hydro1D & operator*=(const double &d)
Definition: state.cpp:1409
~State2D()
Definition: state.cpp:1681
size_t ns
Definition: state.h:642
Algorithms
valarray< double > & temperaturearray() const
Definition: state.h:549
EMF1D & operator*=(const complex< double > &d)
Definition: state.cpp:620
size_t mmax
Definition: state.h:381
double ma
Definition: state.h:382
valarray< double > getpressure()
Definition: state.cpp:1081
SHarmonic2D & Filterp(size_t N)
Definition: state.cpp:364
size_t numx() const
Definition: state.h:197
Field1D & Dx()
Definition: state.cpp:450
~Field2D()
Definition: state.cpp:508
~EMF1D()
Definition: state.cpp:591
EMF2D & EMF() const
Definition: state.h:664
void checknan()
Definition: state.cpp:1103
SHarmonic2D & mxaxis(const valarray< complex< double > > &shmulti)
Definition: state.cpp:307
vector< DistFunc2D > * sp
Definition: state.h:639
A 1D Field.
Definition: state.h:184
SHarmonic2D & mxy_matrix(Array2D< complex< double > > &shmultiM)
Definition: state.cpp:352
SHarmonic1D & operator()(int i)
Definition: state.cpp:838
A 2D Field.
Definition: state.h:233
Underlying data structures.
Field2D & operator+=(const complex< double > &d)
Definition: state.cpp:537
DistFunc1D & operator=(const complex< double > &d)
Definition: state.cpp:866
EMF1D & operator=(const complex< double > &d)
Definition: state.cpp:599
State2D & operator-=(const State2D &other)
Definition: state.cpp:1729
SHarmonic2D(size_t nump, size_t numx, size_t numy)
Definition: state.cpp:244
Field2D & Dy()
Definition: state.cpp:562
EMF2D & operator-=(const complex< double > &d)
Definition: state.cpp:729
size_t dim() const
Definition: state.h:468
State1D & operator+=(const State1D &other)
Definition: state.cpp:1594
Field1D & operator*=(const complex< double > &d)
Definition: state.cpp:409
A Collection of relevant 1D Hydrodynamic Quantities.
Definition: state.h:507
size_t ldim() const
Definition: state.h:469
size_t nump() const
Definition: state.h:136
SHarmonic2D & myaxis(const valarray< complex< double > > &shmulti)
Definition: state.cpp:311
Field2D & operator*=(const complex< double > &d)
Definition: state.cpp:527
DistFunc1D & Filterp()
Definition: state.cpp:934
~Hydro1D()
Definition: state.cpp:1367
State1D & operator*=(const State1D &other)
Definition: state.cpp:1576
Hydro1D(size_t numx, double _mass, double _charge)
Definition: state.cpp:1337
double mass() const
Definition: state.h:400
size_t numx() const
Definition: state.h:522
double ma
Definition: state.h:454
SHarmonic2D & mpaxis(const valarray< complex< double > > &shmulti)
Definition: state.cpp:303
EMF2D & operator+=(const complex< double > &d)
Definition: state.cpp:716
size_t numy() const
Definition: state.h:138
DistFunc2D & DF(size_t s)
Definition: state.h:656
double pmx
Definition: state.h:382
valarray< double > * hvz
Definition: state.h:510
double charge
Definition: state.h:454
EMF1D & operator-=(const complex< double > &d)
Definition: state.cpp:646
SHarmonic2D * operator()(size_t i)
Definition: state.cpp:1196
SHarmonic2D & operator+=(const complex< double > &d)
Definition: state.cpp:282
Array2D & Dd2()
Definition: lib-array.h:556
DistFunc2D & operator*=(const complex< double > &d)
Definition: state.cpp:1249
SHarmonic2D & operator*=(const complex< double > &d)
Definition: state.cpp:273
SHarmonic1D & mxaxis(const valarray< complex< double > > &shmulti)
Definition: state.cpp:126
State1D(size_t nx, vector< size_t > l0, vector< size_t > m0, vector< size_t > np, vector< double > pmax, vector< double > q, vector< double > ma, double hydromass, double hydrocharge)
Definition: state.cpp:1512
Array2D< complex< double > > * sh
Definition: state.h:60
Field1D & operator-=(const complex< double > &d)
Definition: state.cpp:431
Array2D< complex< double > > & array() const
Definition: state.h:245
Field1D & Re()
Definition: state.cpp:441
valarray< double > * hvy
Definition: state.h:510
EMF1D * flds
Definition: state.h:580
Array2D< double > getcurrent() const
Definition: state.cpp:1050
size_t dim() const
Definition: state.h:286
void checknan()
Definition: state.cpp:218
State1D & operator=(const State1D &other)
Definition: state.cpp:1554
EMF1D(size_t nx)
Definition: state.cpp:581
size_t lmax
Definition: state.h:453
Field2D & operator=(const complex< double > &d)
Definition: state.cpp:516
void checknan()
Definition: state.cpp:1630
SHarmonic1D & Re()
Definition: state.cpp:130
size_t numx() const
Definition: state.h:72
size_t dim() const
Definition: state.h:395
~SHarmonic1D()
Definition: state.cpp:72
size_t sz
Definition: state.h:381
DistFunc2D & operator-=(const complex< double > &d)
Definition: state.cpp:1298
A 2D Spherical Harmonic.
Definition: state.h:122
A 1D Spherical Harmonic.
Definition: state.h:57
SHarmonic1D & Dp()
Definition: state.cpp:139
valarray< complex< double > > & array() const
Definition: state.h:196
State1D & operator-=(const State1D &other)
Definition: state.cpp:1612
~DistFunc1D()
Definition: state.cpp:831
size_t dim() const
Definition: state.h:70
Field1D & operator=(const complex< double > &d)
Definition: state.cpp:394
SHarmonic1D(size_t nump, size_t numx)
The constructor requires nump, and numx as inputs.
Definition: state.cpp:63
valarray< double > & vyarray() const
Definition: state.h:547
T relativistic_invg_moment(const vector< T > q, const valarray< T > x, const int p)
Definition: state.h:577
~Field1D()
Definition: state.cpp:386
EMF2D & operator*=(const complex< double > &d)
Definition: state.cpp:703
Definition: state.h:637
Hydro1D & operator+=(const double &d)
Definition: state.cpp:1441
valarray< double > * hn
Definition: state.h:510
State2D & operator=(const State2D &other)
Definition: state.cpp:1689
double pmax() const
Definition: state.h:398
Array3D< complex< double > > & array() const
Definition: state.h:134
valarray< double > * ht
Definition: state.h:510
SHarmonic1D & operator+=(const complex< double > &d)
Definition: state.cpp:101
valarray< double > & Zarray() const
Definition: state.h:550
Field1D & operator+=(const complex< double > &d)
Definition: state.cpp:422
Hydro1D & HYDRO()
Definition: state.h:613
DistFunc1D(size_t l, size_t m, size_t np, double pma, size_t nx, double q, double _ma)
Definition: state.cpp:749
DistFunc1D & operator+=(const complex< double > &d)
Definition: state.cpp:904
EMF1D & operator+=(const complex< double > &d)
Definition: state.cpp:633
size_t m0() const
Definition: state.h:472
Field2D(size_t numx, size_t numy)
Definition: state.cpp:499
size_t nump() const
Definition: state.h:71
size_t lmax
Definition: state.h:381
vector< SHarmonic1D > * df
Definition: state.h:380
double mass() const
Definition: state.h:523
size_t m0() const
Definition: state.h:397
double q() const
Definition: state.h:399
EMF2D * flds
Definition: state.h:640
Field2D & FLD(size_t ip) const
Definition: state.h:665
~SHarmonic2D()
Definition: state.cpp:253
double q() const
Definition: state.h:473
DistFunc1D & DF(size_t s)
Definition: state.h:602
SHarmonic2D & operator=(const complex< double > &d)
Definition: state.cpp:262
Array2D< int > ind
Definition: state.h:457
size_t mmax
Definition: state.h:453
Field2D & Dx()
Definition: state.cpp:556
size_t numx() const
Definition: state.h:137
DistFunc1D & operator-=(const complex< double > &d)
Definition: state.cpp:919
size_t l0() const
Definition: state.h:471
Fields, Distributions, Harmonics, States - Declarations.
valarray< double > * hz
Definition: state.h:510
valarray< double > & densityarray() const
Definition: state.h:545
valarray< double > getdensity()
Definition: state.cpp:945
valarray< double > & vzarray() const
Definition: state.h:548
Definition: state.h:271
State2D & operator+=(const State2D &other)
Definition: state.cpp:1717
An EMF2D is the container for the 6 EM fields in a 2D-3P code.
Definition: state.h:326
DistFunc1D & operator*=(const complex< double > &d)
Definition: state.cpp:889
size_t numy() const
Definition: state.h:247
DistFunc2D & operator+=(const complex< double > &d)
Definition: state.cpp:1271
Array2D & Dd1()
Definition: lib-array.h:507
State2D & operator*=(const State2D &other)
Definition: state.cpp:1705
Array2D< complex< double > > & array() const
To retrieve the the array that stores the information.
Definition: state.h:69
~DistFunc2D()
Definition: state.cpp:1183
size_t ns
Definition: state.h:586
Array2D & Filterd1(size_t N)
Definition: lib-array.h:604
Array2D< int > indx() const
Definition: state.h:402
valarray< T > MakeCAxis(const T min, const T max, const size_t N)
SHarmonic2D & Dx()
Definition: state.cpp:341
SHarmonic1D & Dx()
Definition: state.cpp:185
Field1D & FLD(size_t ip) const
Definition: state.h:611
SHarmonic2D & operator-=(const complex< double > &d)
Definition: state.cpp:291
valarray< double > * hvx
Definition: state.h:510
size_t dim() const
Definition: state.h:338
Hydro1D * hydro
Definition: state.h:581
size_t l0() const
Definition: state.h:396
SHarmonic2D & Dy()
Definition: state.cpp:347
size_t mdim() const
Definition: state.h:470
~State1D()
Definition: state.cpp:1545
SHarmonic1D & operator*=(const complex< double > &d)
Definition: state.cpp:92
Field1D(size_t numx)
Definition: state.cpp:377
valarray< double > & vxarray() const
Definition: state.h:546
SHarmonic1D & Filterp(size_t N)
Definition: state.cpp:212
vector< SHarmonic2D > * df
Definition: state.h:452
DistFunc2D(size_t l, size_t m, size_t np, size_t nx, size_t ny, double q, double _ma)
Definition: state.cpp:1131
Field2D & operator-=(const complex< double > &d)
Definition: state.cpp:546
size_t sz
Definition: state.h:453
DistFunc2D & operator=(const complex< double > &d)
Definition: state.cpp:1219
SHarmonic1D & operator-=(const complex< double > &d)
Definition: state.cpp:110
SHarmonic1D & operator=(const complex< double > &d)
Definition: state.cpp:81
Array2D< int > ind
Definition: state.h:384
Hydro1D & operator-=(const double &d)
Definition: state.cpp:1474
vector< DistFunc1D > * sp
Definition: state.h:579
~EMF2D()
Definition: state.cpp:674
size_t Species() const
Definition: state.h:596
EMF2D(size_t nx, size_t ny)
Definition: state.cpp:664
valarray< int > filter_ceiling
Definition: state.h:385
double charge() const
Definition: state.h:524
The 1D distribution function is the container for all SHarmonic1D per species.
Definition: state.h:376
T moment(const vector< T > q, const vector< T > x, const int p)
double mass() const
Definition: state.h:474
The 2D distribution function is the container for all SHarmonic2D per species.
Definition: state.h:449
EMF1D & EMF() const
Definition: state.h:610
State2D(size_t nx, size_t ny, vector< size_t > l0, vector< size_t > m0, vector< size_t > np, vector< double > q, vector< double > ma)
Definition: state.cpp:1654
Hydro1D & operator=(const double &d)
Definition: state.cpp:1377
size_t numx() const
Definition: state.h:246
SHarmonic1D & mpaxis(const valarray< complex< double > > &shmulti)
Definition: state.cpp:122
Numerical Methods - Declarations.