1 /**
2 Ported to dlang 2015 by Laeeth Isharc
3 */
4 /**
5 This is a work in progress and does not yet compile
6 */
7
8 module kaleidic.api.mathgl.data;
9 /+
10 /// Class for working with data array
11 class MglData
12 {
13 //public : using MglDataA : : Momentum;
14 long nx; ///< number of points in 1st dimensions ('x' dimension)
15 long ny; ///< number of points in 2nd dimensions ('y' dimension)
16 long nz; ///< number of points in 3d dimensions ('z' dimension)
17 mreal* a; ///< data array
18 string id; ///< column (or slice) names
19 bool useLink; ///< use external data (i.e. don't free it)
20
21 /// Initiate by other MglData variable
22 this(const MglData* d)
23 {
24 a = 0;
25 mgl_data_set(this, & d);
26 } // NOTE: must be constructor for MglData& to exclude copy one
27
28 static if(HaveRval)
29 {
30 this(MglData** d)
31 {
32 this.nx=d.nx;
33 this.ny=d.ny;
34 this.nz=d.nz;
35 thia.a=d.a;
36 this.id=d.id;
37 this.useLink=d.useLink;
38 //this. s = d.s;
39 //this.temp = d.temp;
40 this.func = d.func;
41 this.o = d.o;
42 d.a = 0;
43 d.func = 0;
44 }
45 }
46
47 this(const MglDataA* d)
48 {
49 a = 0;
50 if (d)
51 mgl_data_set(this, d);
52 else
53 mgl_data_create(this, 1, 1, 1);
54 }
55
56 this(MglData * d) // NOTE: Variable d will be deleted!!!
57 {
58 if (d is null)
59 {
60 nx = d.nx;
61 ny = d.ny;
62 nz = d.nz;
63 a = d.a;
64 d.a = 0;
65 temp = d.temp;
66 func = d.func;
67 o = d.o;
68 s = d.s;
69 id = d.id;
70 useLink = d.useLink;
71 delete d;
72 }
73 else
74 {
75 a = 0;
76 create(1);
77 }
78 }
79
80 /// Initiate by flat array
81 this(int size, const float * d)
82 {
83 a = 0;
84 set(d, size);
85 }
86 this(int rows, int cols, const float * d)
87 {
88 a = 0;
89 set(d, cols, rows);
90 }
91 this(int size, const double * d)
92 {
93 a = 0;
94 set(d, size);
95 }
96 this(int rows, int cols, const double * d)
97 {
98 a = 0;
99 set(d, cols, rows);
100 }
101 this(const double * d, int size)
102 {
103 a = 0;
104 set(d, size);
105 }
106 this(const double * d, int rows, int cols)
107 {
108 a = 0;
109 set(d, cols, rows);
110 }
111 this(const float * d, int size)
112 {
113 a = 0;
114 set(d, size);
115 }
116 this(const float * d, int rows, int cols)
117 {
118 a = 0;
119 set(d, cols, rows);
120 }
121 /// Read data from file
122 this(string fname)
123 {
124 a = 0;
125 Read(fname);
126 }
127 /// allocate the memory for data array and initialize it zero
128 this(long xx = 1, long yy = 1, long zz = 1)
129 {
130 a = 0;
131 create(xx, yy, zz);
132 }
133
134 /// Delete the array
135 ~this()
136 {
137 //if (!useLink && a)
138 // delete[] a;
139 }
140
141 mreal getVal(long i, long j = 0, long k = 0) const
142 {
143 return mgl_data_get_value(this, i, j, k);
144 }
145
146 void setVal(mreal f, long i, long j = 0, long k = 0)
147 {
148 mgl_data_set_value(this, f, i, j, k);
149 }
150
151 /// Get sizes
152 long getNx() const
153 {
154 return nx;
155 }
156
157 long getNy() const
158 {
159 return ny;
160 }
161
162 long getNz() const
163 {
164 return nz;
165 }
166
167 /// Link external data array (don't delete it at exit)
168 void link(mreal* A, long NX, long NY = 1, long NZ = 1)
169 {
170 mgl_data_link(this, A, NX, NY, NZ);
171 }
172
173 void link(MglData* d)
174 {
175 link(d.a, d.nx, d.ny, d.nz);
176 }
177 /// allocate memory and copy the data from the gsl_vector
178 void set(gsl_vector* m)
179 {
180 mgl_data_set_vector(this, m);
181 }
182
183 /// allocate memory and copy the data from the gsl_matrix
184 void set(gsl_matrix* m)
185 {
186 mgl_data_set_matrix(this, m);
187 }
188
189 /// allocate memory and copy the data from the (float *) array
190 void set(in float* A, long NX, long NY = 1, long NZ = 1)
191 {
192 mgl_data_set_float(this, A, NX, NY, NZ);
193 }
194
195 /// allocate memory and copy the data from the (double *) array
196 void set(const double* A, long NX, long NY = 1, long NZ = 1)
197 {
198 mgl_data_set_double(this, A, NX, NY, NZ);
199 }
200
201 /// allocate memory and copy the data from the (float **) array
202 void set(in float** A, long N1, long N2)
203 {
204 mgl_data_set_float2(this, A, N1, N2);
205 }
206 /// allocate memory and copy the data from the (double **) array
207 void set(in double** A, long N1, long N2)
208 {
209 mgl_data_set_double2(this, A, N1, N2);
210 }
211 /// allocate memory and copy the data from the (float ***) array
212 void set(in float** A, long N1, long N2, long N3)
213 {
214 mgl_data_set_float3(this, A, N1, N2, N3);
215 }
216 /// allocate memory and copy the data from the (double ***) array
217 void set(in double** A, long N1, long N2, long N3)
218 {
219 mgl_data_set_double3(this, A, N1, N2, N3);
220 }
221 /// allocate memory and scanf the data from the string
222 void set(string str, long NX, long NY = 1, long NZ = 1)
223 {
224 mgl_data_set_values(this, str.toStringz, NX, NY, NZ);
225 }
226
227 /// Import data from abstract type
228 void set(HCDT dat)
229 {
230 mgl_data_set(this, dat);
231 }
232
233 void set(const MglDataA* dat)
234 {
235 mgl_data_set(this, & dat);
236 }
237 /// allocate memory and copy data from std::vector<T>
238 void set(int[] d)
239 {
240 if (d.length < 1)
241 return;
242 create(d.length);
243 for (long i = 0; i < nx; i++)
244 a[i] = d[i];
245 }
246 void set(float[] d)
247 {
248 if (d.length < 1)
249 return;
250 create(d.length);
251 foreach(i;0..nx)
252 a[i] = d[i];
253 }
254 void set(double[] d)
255 {
256 if (d.length < 1)
257 return;
258 create(d.length);
259 foreach(i;0..nx)
260 a[i] = d[i];
261 }
262
263 /// create or recreate the array with specified size and fill it by zero
264 void create(long mx, long my = 1, long mz = 1)
265 {
266 mgl_data_create(this, mx, my, mz);
267 }
268
269 /// Rearange data dimensions
270 void rearrange(long mx, long my = 0, long mz = 0)
271 {
272 mgl_data_rearrange(this, mx, my, mz);
273 }
274
275 /// Transpose dimensions of the data (generalization of Transpose)
276 void transpose(string dim = "yx")
277 {
278 mgl_data_transpose(this, dim);
279 }
280
281 /// Extend data dimensions
282 void extend(long n1, long n2 = 0)
283 {
284 mgl_data_extend(this, n1, n2);
285 }
286
287 /// Reduce size of the data
288 void squeeze(long rx, long ry = 1, long rz = 1, bool smooth = false)
289 {
290 mgl_data_squeeze(this, rx, ry, rz, smooth);
291 }
292
293 /// Crop the data
294 void crop(long n1, long n2, char dir = 'x')
295 {
296 mgl_data_crop(this, n1, n2, dir);
297 }
298
299 /// Insert data rows/columns/slices
300 void insert(char dir, long at = 0, long num = 1)
301 {
302 mgl_data_insert(this, dir, at, num);
303 }
304
305 /// Delete data rows/columns/slices
306 void deleteItems(char dir, long at = 0, long num = 1)
307 {
308 mgl_data_delete(this, dir, at, num);
309 }
310
311 /// Remove rows with duplicate values in column id
312 void clean(long id)
313 {
314 mgl_data_clean(this, id);
315 }
316
317 /// Join with another data array
318 void join(const MglDataA* d)
319 {
320 mgl_data_join(this, *d);
321 }
322
323 /// Modify the data by specified formula
324 void modify(string eq, long dim = 0)
325 {
326 mgl_data_modify(this, eq.toStringz, dim);
327 }
328
329 /// Modify the data by specified formula
330 void modify(string eq, in MglDataA* vdat, in MglDataA* wdat)
331 {
332 mgl_data_modify_vw(this, eq.to!stringz, *vdat, * wdat);
333 }
334 /// Modify the data by specified formula
335 void modify(string eq, const MglDataA* vdat)
336 {
337 mgl_data_modify_vw(this, eq.toStringz, *vdat, 0);
338 }
339 /// Modify the data by specified formula assuming x,y,z in range [r1,r2]
340 void fill(HMGL gr, string eq, string opt = "")
341 {
342 mgl_data_fill_eq(gr, this, eq.toStringz, 0, 0, opt);
343 }
344
345 void fill(HMGL gr, string eq, const MglDataA* vdat, string opt = "")
346 {
347 mgl_data_fill_eq(gr, this, eq.toStringz, *vdat, 0, opt.toStringz);
348 }
349
350 void fill(HMGL gr, string eq, const MglDataA* vdat, const MglDataA* wdat, string opt = "")
351 {
352 mgl_data_fill_eq(gr, this, eq.toStringz, *vdat, * wdat, opt.toStringz);
353 }
354 /// Equidistantly fill the data to range [x1,x2] in direction dir
355 void fill(mreal x1, mreal x2 = mglNaN, char dir = 'x')
356 {
357 mgl_data_fill(this, x1, x2, dir);
358 }
359
360 /// fill the data by interpolated values of vdat parametrically depended on xdat,ydat,zdat for x,y,z in range [p1,p2] using global spline
361 void refillGS(in MglDataA* xdat, const MglDataA* vdat, mreal x1, mreal x2,
362 long sl = - 1)
363 {
364 mgl_data_refill_gs(this, *xdat, & vdat, x1, x2, sl);
365 }
366 /// fill the data by interpolated values of vdat parametrically depended on xdat,ydat,zdat for x,y,z in range [p1,p2]
367 void refill(in MglDataA* xdat, in MglDataA* vdat, mreal x1, mreal x2, long sl = - 1)
368 {
369 mgl_data_refill_x(this, *xdat, & vdat, x1, x2, sl);
370 }
371 void refill(in MglDataA* xdat, in MglDataA* vdat, MglPoint p1, MglPoint p2,
372 long sl = - 1)
373 {
374 mgl_data_refill_x(this, *xdat, & vdat, p1.x, p2.x, sl);
375 }
376 void refill(in MglDataA* xdat, in MglDataA* ydat, in MglDataA* vdat,
377 MglPoint p1, MglPoint p2, long sl = - 1)
378 {
379 mgl_data_refill_xy(this, *xdat, & ydat, & vdat, p1.x, p2.x, p1.y, p2.y,
380 sl);
381 }
382 void refill(in MglDataA* xdat, in MglDataA* ydat, in MglDataA* zdat,
383 in MglDataA* vdat, MglPoint p1, MglPoint p2)
384 {
385 mgl_data_refill_xyz(this, *xdat, & ydat, & zdat, & vdat, p1.x, p2.x,
386 p1.y, p2.y, p1.z, p2.z);
387 }
388 /// fill the data by interpolated values of vdat parametrically depended on xdat,ydat,zdat for x,y,z in axis range of gr
389 void refill(HMGL gr, in MglDataA* xdat, in MglDataA* vdat,
390 long sl = - 1, string opt = "")
391 {
392 mgl_data_refill_gr(gr, this, *xdat, 0, 0, & vdat, sl, opt);
393 }
394 void refill(HMGL gr, in MglDataA* xdat, in MglDataA* ydat,
395 in MglDataA* vdat, long sl = - 1, string opt = "")
396 {
397 mgl_data_refill_gr(gr, this, *xdat, & ydat, 0, & vdat, sl, opt);
398 }
399 void refill(HMGL gr, in MglDataA* xdat, in MglDataA* ydat,
400 in MglDataA* zdat, in MglDataA* vdat, string opt = "")
401 {
402 mgl_data_refill_gr(gr, this, *xdat, & ydat, & zdat, & vdat, - 1, opt);
403 }
404 /// set the data by triangulated surface values assuming x,y,z in axis range of gr
405 void grid(HMGL gr, in MglDataA* x, in MglDataA* y, in MglDataA* z, string opt = "")
406 {
407 mgl_data_grid(gr, this, *x, *y, *z, opt.toStringz);
408 }
409 /// set the data by triangulated surface values assuming x,y,z in range [p1, p2]
410 void grid(in MglDataA* xdat, in MglDataA* ydat, in MglDataA* vdat,
411 MglPoint p1, MglPoint p2)
412 {
413 mgl_data_grid_xy(this, *xdat, & ydat, & vdat, p1.x, p2.x, p1.y, p2.y);
414 }
415 /// Put value to data element(s)
416 void put(mreal val, long i = -1, long j = -1, long k = -1)
417 {
418 mgl_data_put_val(this, val, i, j, k);
419 }
420
421 /// Put array to data element(s)
422 void put(in MglDataA* dat, long i = - 1, long j = - 1, long k = - 1)
423 {
424 mgl_data_put_dat(this, & dat, i, j, k);
425 }
426 /// set names for columns (slices)
427 void setColumnId(string ids)
428 {
429 mgl_data_set_id(this, ids);
430 }
431
432 /// Make new id
433 void newId()
434 {
435 id.clear();
436 }
437
438 /// Read data from tab-separated text file with auto determining size
439 bool read(string fname)
440 {
441 return mgl_data_read(this, fname);
442 }
443
444 /// Read data from text file with specifeid size
445 bool read(string fname, long mx, long my = 1, long mz = 1)
446 {
447 return mgl_data_read_dim(this, fname.toStringz, mx, my, mz);
448 }
449
450 /// Import data array from PNG file according color scheme
451 void importData(string fname, string scheme, mreal v1 = 0, mreal v2 = 1)
452 {
453 mgl_data_import(this, fname.toStringz, scheme.toStringz, v1, v2);
454 }
455
456 /// Read data from tab-separated text files with auto determining size which filenames are result of sprintf(fname,templ,t) where t=from:step:to
457 bool readRange(string templ, double from, double to, double step = 1, bool as_slice = false)
458 {
459 return mgl_data_read_range(this, templ.toStringz, from, to, step, as_slice);
460 }
461
462 /// Read data from tab-separated text files with auto determining size which filenames are satisfied to template (like "t_*.dat")
463 bool readall(string templ, bool as_slice = false)
464 {
465 return mgl_data_read_all(this, templ.toStringz, as_slice);
466 }
467
468 /// Read data from text file with size specified at beginning of the file
469 bool readMat(string fname, long dim = 2)
470 {
471 return mgl_data_read_mat(this, fname.toStringz, dim);
472 }
473
474 /// Read data array from HDF file (parse HDF4 and HDF5 files)
475 int readHDF(string fname, ubyte[] data)
476 {
477 return mgl_data_read_hdf(this, fname.toStringz, data.ptr);
478 }
479
480 /// Get column (or slice) of the data filled by formulas of named columns
481 MglData Column(string eq) const
482 {
483 return MglData(true, mgl_data_column(this, eq.toStringz));
484 }
485
486 /// Get momentum (1D-array) of data along direction 'dir'. String looks like "x1" for median in x-direction, "x2" for width in x-dir and so on.
487 MglData Momentum(char dir, string how) const
488 {
489 return MglData(true, mgl_data_momentum(this, dir, how.toStringz));
490 }
491
492 /// Get sub-array of the data with given fixed indexes
493 MglData SubData(long xx, long yy = -1, long zz = -1) const
494 {
495 return MglData(true, mgl_data_subdata(this, xx, yy, zz));
496 }
497
498 MglData SubData(in MglDataA* xx, in MglDataA* yy, in MglDataA* zz) const
499 {
500 return MglData(true, mgl_data_subdata_ext(this, & xx, & yy, & zz));
501 }
502 MglData SubData(in MglDataA* xx, in MglDataA* yy) const
503 {
504 return MglData(true, mgl_data_subdata_ext(this, & xx, & yy, 0));
505 }
506 MglData subData(in MglDataA* xx) const
507 {
508 return MglData(true, mgl_data_subdata_ext(this, & xx, 0, 0));
509 }
510 /// Get trace of the data array
511 MglData trace() const
512 {
513 return MglData(true, mgl_data_trace(this));
514 }
515
516 /// create n-th points distribution of this data values in range [v1, v2]
517 MglData hist(long n, mreal v1 = 0, mreal v2 = 1, long nsub = 0) const
518 {
519 return MglData(true, mgl_data_hist(this, n, v1, v2, nsub));
520 }
521
522 /// create n-th points distribution of this data values in range [v1, v2] with weight w
523 MglData hist(in MglDataA* w, long n, mreal v1 = 0, mreal v2 = 1, long nsub = 0) const
524 {
525 return MglData(true, mgl_data_hist_w(this, & w, n, v1, v2, nsub));
526 }
527 /// Get array which is result of summation in given direction or directions
528 MglData sum(string dir) const
529 {
530 return MglData(true, mgl_data_sum(this, dir));
531 }
532
533 /// Get array which is result of maximal values in given direction or directions
534 MglData max(string dir) const
535 {
536 return MglData(true, mgl_data_max_dir(this, dir));
537 }
538
539 /// Get array which is result of minimal values in given direction or directions
540 MglData min(string dir) const
541 {
542 return MglData(true, mgl_data_min_dir(this, dir));
543 }
544
545 /// Get the data which is direct multiplication (like, d[i,j] = this[i]*a[j] and so on)
546 MglData combine(in MglDataA* dat) const
547 {
548 return MglData(true, mgl_data_combine(this, & dat));
549 }
550 /// Resize the data to new size of box [x1,x2]*[y1,y2]*[z1,z2]
551 MglData resize(long mx, long my = 0, long mz = 0, mreal x1 = 0, mreal x2 = 1,
552 mreal y1 = 0, mreal y2 = 1, mreal z1 = 0, mreal z2 = 1) const
553 {
554 return MglData(true, mgl_data_resize_box(this, mx, my, mz, x1, x2, y1, y2,
555 z1, z2));
556 }
557
558 /// Get array which values is result of interpolation this for coordinates from other arrays
559 MglData evaluate(in MglData* idat, bool norm = true) const
560 {
561 return MglData(true, mgl_data_evaluate(this, & idat, 0, 0, norm));
562 }
563 MglData evaluate(in MglData* idat, in MglData* jdat, bool norm = true) const
564 {
565 return MglData(true, mgl_data_evaluate(this, & idat, & jdat, 0, norm));
566 }
567 MglData evaluate(in MglData* idat, in MglData* jdat, in MglData* kdat,
568 bool norm = true) const
569 {
570 return MglData(true, mgl_data_evaluate(this, & idat, & jdat, & kdat, norm));
571 }
572 /// Find roots for set of nonlinear equations defined by textual formula
573 MglData roots(string func, char var = 'x') const
574 {
575 return MglData(true, mgl_data_roots(func, this, var));
576 }
577
578 /// Find correlation with another data arrays
579 MglData correl(in MglDataA* dat, string dir) const
580 {
581 return MglData(true, mgl_data_correl(this, & dat, dir));
582 }
583 /// Find auto correlation function
584 MglData autoCorrel(string dir) const
585 {
586 return MglData(true, mgl_data_correl(this, this, dir));
587 }
588
589 /// Cumulative summation the data in given direction or directions
590 void cumSum(string dir)
591 {
592 mgl_data_cumsum(this, dir);
593 }
594
595 /// Integrate (cumulative summation) the data in given direction or directions
596 void integral(string dir)
597 {
598 mgl_data_integral(this, dir);
599 }
600
601 /// Differentiate the data in given direction or directions
602 void diff(string dir)
603 {
604 mgl_data_diff(this, dir);
605 }
606
607 /// Differentiate the parametrically specified data along direction v1 with v2=const
608 void diff(ref MglDataA v1, ref MglDataA v2)
609 {
610 mgl_data_diff_par(this, v1, v2, 0);
611 }
612 /// Differentiate the parametrically specified data along direction v1 with v2,v3=const
613 void diff(ref MglDataA v1,ref MglDataA v2, ref MglDataA v3)
614 {
615 mgl_data_diff_par(this, v1, v2, v3);
616 }
617 /// Double-differentiate (like Laplace operator) the data in given direction
618 void Diff2(string dir)
619 {
620 mgl_data_diff2(this, dir);
621 }
622
623 /// Swap left and right part of the data in given direction (useful for Fourier spectrum)
624 void Swap(string dir)
625 {
626 mgl_data_swap(this, dir);
627 }
628
629 /// Roll data along direction dir by num slices
630 void Roll(char dir, long num)
631 {
632 mgl_data_roll(this, dir, num);
633 }
634
635 /// Mirror the data in given direction (useful for Fourier spectrum)
636 void Mirror(string dir)
637 {
638 mgl_data_mirror(this, dir);
639 }
640
641 /// Sort rows (or slices) by values of specified column
642 void Sort(long idx, long idy = -1)
643 {
644 mgl_data_sort(this, idx, idy);
645 }
646
647 /// set as the data envelop
648 void Envelop(char dir = 'x')
649 {
650 mgl_data_envelop(this, dir);
651 }
652
653 /// Remove phase jump
654 void Sew(string dirs = "xyz", mreal da = 2 * mglPi)
655 {
656 mgl_data_sew(this, dirs, da);
657 }
658
659 /// Smooth the data on specified direction or directions
660 void Smooth(string dirs = "xyz", mreal delta = 0)
661 {
662 mgl_data_smooth(this, dirs, delta);
663 }
664
665 /// Normalize the data to range [v1,v2]
666 void Norm(mreal v1 = 0, mreal v2 = 1, bool sym = false, long dim = 0)
667 {
668 mgl_data_norm(this, v1, v2, sym, dim);
669 }
670
671 /// Normalize the data to range [v1,v2] slice by slice
672 void NormSl(mreal v1 = 0, mreal v2 = 1, char dir = 'z', bool keep_en = true, bool sym = false)
673 {
674 mgl_data_norm_slice(this, v1, v2, dir, keep_en, sym);
675 }
676
677 /// Apply Hankel transform
678 void Hankel(string dir)
679 {
680 mgl_data_hankel(this, dir);
681 }
682
683 /// Apply Sin-Fourier transform
684 void SinFFT(string dir)
685 {
686 mgl_data_sinfft(this, dir);
687 }
688
689 /// Apply Cos-Fourier transform
690 void CosFFT(string dir)
691 {
692 mgl_data_cosfft(this, dir);
693 }
694
695 /// fill data by 'x'/'k' samples for Hankel ('h') or Fourier ('f') transform
696 void fillSample(string how)
697 {
698 mgl_data_fill_sample(this, how);
699 }
700
701 /// Return an approximated x-value (root) when dat(x) = val
702 mreal Solve(mreal val, bool use_spline = true, long i0 = 0) const
703 {
704 return mgl_data_solve_1d(this, val, use_spline, i0);
705 }
706
707 /// Return an approximated value (root) when dat(x) = val
708 MglData solve(mreal val, char dir, bool norm = true) const
709 {
710 return MglData(true, mgl_data_solve(this, val, dir, 0, norm));
711 }
712
713 MglData solve(mreal val, char dir, in MglData* i0, bool norm = true) const
714 {
715 return MglData(true, mgl_data_solve(this, val, dir, & i0, norm));
716 }
717
718 /// Interpolate by cubic spline the data to given point x=[0...nx-1], y=[0...ny-1], z=[0...nz-1]
719 mreal spline(mreal x, mreal y = 0, mreal z = 0) const
720 {
721 return mgl_data_spline(this, x, y, z);
722 }
723
724 /// Interpolate by cubic spline the data to given point x,\a y,\a z which normalized in range [0, 1]
725 mreal spline1(mreal x, mreal y = 0, mreal z = 0) const
726 {
727 return mgl_data_spline(this, x * (nx - 1), y * (ny - 1), z * (nz - 1));
728 }
729
730 /// Interpolate by linear function the data to given point x=[0...nx-1], y=[0...ny-1], z=[0...nz-1]
731 mreal linear(mreal x, mreal y = 0, mreal z = 0) const
732 {
733 return mgl_data_linear(this, x, y, z);
734 }
735
736 /// Interpolate by line the data to given point x,\a y,\a z which normalized in range [0, 1]
737 mreal linear1(mreal x, mreal y = 0, mreal z = 0) const
738 {
739 return mgl_data_linear(this, x * (nx - 1), y * (ny - 1), z * (nz - 1));
740 }
741
742 /// Interpolate by cubic spline the data and return its derivatives at given point x=[0...nx-1], y=[0...ny-1], z=[0...nz-1]
743 mreal spline(ref MglPoint dif, mreal x, mreal y = 0, mreal z = 0) const
744 {
745 return mgl_data_spline_ext(this, x, y, z, & (dif.x), & (dif.y), & (dif.z));
746 }
747 /// Interpolate by cubic spline the data and return its derivatives at given point x,\a y,\a z which normalized in range [0, 1]
748 mreal spline1(ref MglPoint dif, mreal x, mreal y = 0, mreal z = 0) const
749 {
750 mreal res = mgl_data_spline_ext(this, x * (nx - 1), y * (ny - 1),
751 z * (nz - 1), &(dif.x), &(dif.y), &(dif.z));
752 dif.x *= nx > 1 ? nx - 1 : 1;
753 dif.y *= ny > 1 ? ny - 1 : 1;
754 dif.z *= nz > 1 ? nz - 1 : 1;
755 return res;
756 }
757 /// Interpolate by linear function the data and return its derivatives at given point x=[0...nx-1], y=[0...ny-1], z=[0...nz-1]
758 mreal linear(ref MglPoint dif, mreal x, mreal y = 0, mreal z = 0) const
759 {
760 return mgl_data_linear_ext(this, x, y, z, & (dif.x), & (dif.y), & (dif.z));
761 }
762 /// Interpolate by line the data and return its derivatives at given point x,\a y,\a z which normalized in range [0, 1]
763 mreal linear1(ref MglPoint dif, mreal x, mreal y = 0, mreal z = 0) const
764 {
765 mreal res = mgl_data_linear_ext(this, x * (nx - 1), y * (ny - 1),
766 z * (nz - 1), &(dif.x), &(dif.y), &(dif.z));
767 dif.x *= nx > 1 ? nx - 1 : 1;
768 dif.y *= ny > 1 ? ny - 1 : 1;
769 dif.z *= nz > 1 ? nz - 1 : 1;
770 return res;
771 }
772 /**
773 /// Copy data from other MglData variable
774 in MglDataA* operator = (in MglDataA* d)
775 {
776 if (this != & d)
777 mgl_data_set(this, & d);
778 return d;
779 }
780 in MglData* operator = (in MglData* d)
781 {
782 if (this != & d)
783 mgl_data_set(this, & d);
784 return d;
785 }
786 mreal operator = (mreal val)
787 {
788 mgl_data_fill(this, val, val, 'x');
789 return val;
790 }
791 /// Multiply the data by other one for each element
792 void operator *= (in MglDataA* d)
793 {
794 mgl_data_mul_dat(this, & d);
795 }
796 /// Divide the data by other one for each element
797 void operator /= (in MglDataA* d)
798 {
799 mgl_data_div_dat(this, & d);
800 }
801 /// Add the other data
802 void operator += (in MglDataA* d)
803 {
804 mgl_data_add_dat(this, & d);
805 }
806 /// Subtract the other data
807 void operator -= (in MglDataA* d)
808 {
809 mgl_data_sub_dat(this, & d);
810 }
811 /// Multiply each element by the number
812 void operator *= (mreal d)
813 {
814 mgl_data_mul_num(this, d);
815 }
816 /// Divide each element by the number
817 void operator /= (mreal d)
818 {
819 mgl_data_div_num(this, d);
820 }
821 /// Add the number
822 void operator += (mreal d)
823 {
824 mgl_data_add_num(this, d);
825 }
826 /// Subtract the number
827 void operator -= (mreal d)
828 {
829 mgl_data_sub_num(this, d);
830 }
831 #ifndef SWIG/// Direct access to the data cell
832 mreal & operator[](long i)
833 {
834 return a[i];
835 }
836 // NOTE see 13.10 for operator(), operator[] -- m.b. I should add it ???
837 #endif debug
838 {
839 /// Get the value in given cell of the data
840 mreal v(long i, long j = 0, long k = 0) const
841 {
842 return a[i + nx * (j + ny * k)];
843 }
844
845 /// set the value in given cell of the data
846 void set_v(mreal val, long i, long j = 0, long k = 0)
847 {
848 a[i + nx * (j + ny * k)] = val;
849 }
850 }
851 else
852 {
853 /// Get the value in given cell of the data with border checking
854 mreal v(long i, long j = 0, long k = 0) const
855 {
856 return mgl_data_get_value(this, i, j, k);
857 }
858
859 /// set the value in given cell of the data
860 void set_v(mreal val, long i, long j = 0, long k = 0)
861 {
862 mgl_data_set_value(this, val, i, j, k);
863 }
864 }
865 */
866 mreal vthr(long i) const
867 {
868 return a[i];
869 }
870
871 // add for speeding up !!!
872 mreal dvx(long i, long j = 0, long k = 0) const
873 {
874 long i0 = i + nx * (j + ny * k);
875 return i > 0 ? (i < nx - 1 ? (a[i0 + 1] - a[i0 - 1]) / 2 : a[i0] - a[i0 - 1])
876 : a[i0 + 1] - a[i0];
877 }
878
879 mreal dvy(long i, long j = 0, long k = 0) const
880 {
881 long i0 = i + nx * (j + ny * k);
882 return j > 0 ? (j < ny - 1 ? (a[i0 + nx] - a[i0 - nx]) / 2 : a[i0] - a[i0 - nx])
883 : a[i0 + nx] - a[i0];
884 }
885
886 mreal dvz(long i, long j = 0, long k = 0) const
887 {
888 long i0 = i + nx * (j + ny * k), n = nx * ny;
889 return k > 0 ? (k < nz - 1 ? (a[i0 + n] - a[i0 - n]) / 2 : a[i0] - a[i0 - n])
890 : a[i0 + n] - a[i0];
891 }
892 };
893 //-----------------------------------------------------------------------------
894 static if (!SWIG)
895 {
896 /*
897 MglData operator * (in MglDataA* b, in MglDataA* d)
898 {
899 MglData a( & b);
900 a *= d;
901 return a;
902 }
903 MglData operator * (mreal b, in MglDataA* d)
904 {
905 MglData a( & d);
906 a *= b;
907 return a;
908 }
909 MglData operator * (in MglDataA* d, mreal b)
910 {
911 MglData a( & d);
912 a *= b;
913 return a;
914 }
915 MglData operator - (in MglDataA* b, in MglDataA* d)
916 {
917 MglData a( & b);
918 a -= d;
919 return a;
920 }
921 MglData operator - (mreal b, in MglDataA* d)
922 {
923 MglData a( & d);
924 a -= b;
925 return a;
926 }
927 MglData operator - (in MglDataA* d, mreal b)
928 {
929 MglData a( & d);
930 a -= b;
931 return a;
932 }
933 MglData operator + (in MglDataA* b, in MglDataA* d)
934 {
935 MglData a( & b);
936 a += d;
937 return a;
938 }
939 MglData operator + (mreal b, in MglDataA* d)
940 {
941 MglData a( & d);
942 a += b;
943 return a;
944 }
945 MglData operator + (in MglDataA* d, mreal b)
946 {
947 MglData a( & d);
948 a += b;
949 return a;
950 }
951 MglData operator / (in MglDataA* b, in MglDataA* d)
952 {
953 MglData a( & b);
954 a /= d;
955 return a;
956 }
957 MglData operator / (in MglDataA* d, mreal b)
958 {
959 MglData a( & d);
960 a /= b;
961 return a;
962 }
963 bool operator == (in MglData* b, in MglData* d)
964 {
965 if (b.nx != d.nx || b.ny != d.ny || b.nz != d.nz)
966 return false;
967 return !memcmp(b.a, d.a, b.nx * b.ny * b.nz * sizeof(mreal));
968 }
969 bool operator < (in MglDataA* b, in MglDataA* d)
970 {
971 return b.maximal() < d.maximal();
972 }
973 bool operator > (in MglDataA* b, in MglDataA* d)
974 {
975 return b.minimal() > d.minimal();
976 }
977
978 */
979
980 mreal mglLinear(const mreal * a, long nx, long ny, long nz, mreal x, mreal y, mreal z);
981 mreal mglSpline3(const mreal * a, long nx, long ny, long nz, mreal x, mreal y, mreal z, mreal * dx = 0, mreal * dy = 0, mreal * dz = 0);
982 mreal mglSpline3s(const mreal * a, long nx, long ny, long nz, mreal x, mreal y, mreal z);
983 }
984
985 /// Integral data transformation (like Fourier 'f' or 'i', Hankel 'h' or None 'n') for amplitude and phase
986 MglData mglTransformA(in MglDataA* am, in MglDataA* ph, string tr)
987 {
988 return MglData(true, mgl_transform_a( & am, & ph, tr));
989 }
990 /// Integral data transformation (like Fourier 'f' or 'i', Hankel 'h' or None 'n') for real and imaginary parts
991 MglData mglTransform(in MglDataA* re, in MglDataA* im, string tr)
992 {
993 return MglData(true, mgl_transform( & re, & im, tr));
994 }
995
996 /// Apply Fourier transform for the data and save result into it
997 void mglFourier(ref MglData re, ref MglData im, string dir)
998 {
999 mgl_data_fourier(re, im, dir);
1000 }
1001
1002 /// Short time Fourier analysis for real and imaginary parts. Output is amplitude of partial Fourier (result will have size {dn, floor(nx/dn), ny} for dir='x'
1003 MglData mglSTFA(ref MglDataA re, ref MglDataA im, long dn, char dir = 'x')
1004 {
1005 return MglData(true, mgl_data_stfa(re,im, dn, dir));
1006 }
1007
1008 //-----------------------------------------------------------------------------
1009 /// Saves result of PDE solving (|u|^2) for "Hamiltonian" ham with initial conditions ini
1010 MglData mglPDE(HMGL gr, string ham, ref MglDataA* ini_re,
1011 ref MglDataA* ini_im, mreal dz = 0.1, mreal k0 = 100, string opt = "")
1012 {
1013 return MglData(true, mgl_pde_solve(gr, ham, & ini_re, &ini_im, dz, k0, opt));
1014 }
1015
1016 /// Saves result of PDE solving for "Hamiltonian" ham with initial conditions ini along a curve ray (must have nx>=7 - x,y,z,px,py,pz,tau or nx=5 - x,y,px,py,tau)
1017 MglData mglQO2d(string ham, in MglDataA* ini_re, in MglDataA* ini_im,
1018 in MglDataA* ray, mreal r = 1, mreal k0 = 100)
1019 {
1020 return MglData(true, mgl_qo2d_solve(ham, & ini_re, & ini_im, & ray, r, k0, 0,
1021 0));
1022 }
1023
1024 MglData mglQO2d(string ham, in MglDataA* ini_re, in MglDataA* ini_im,
1025 in MglDataA* ray, ref MglData xx, ref MglData yy, mreal r = 1, mreal k0 = 100)
1026 {
1027 return MglData(true, mgl_qo2d_solve(ham, & ini_re, & ini_im, & ray, r, k0, & xx,
1028 & yy));
1029 }
1030 /// Saves result of PDE solving for "Hamiltonian" ham with initial conditions ini along a curve ray (must have nx>=7 - x,y,z,px,py,pz,tau or nx=5 - x,y,px,py,tau)
1031
1032 MglData mglQO3d(string ham, in MglDataA* ini_re, in MglDataA* ini_im,
1033 in MglDataA* ray, mreal r = 1, mreal k0 = 100)
1034 {
1035 return MglData(true, mgl_qo3d_solve(ham, & ini_re, & ini_im, & ray, r, k0, 0,
1036 0, 0));
1037 }
1038
1039 MglData mglQO3d(string ham, ref MglDataA ini_re, ref MglDataA ini_im,
1040 ref MglDataA ray, ref MglData xx, ref MglData yy, ref MglData zz, mreal r = 1, mreal k0 = 100)
1041 {
1042 return MglData(true, mgl_qo3d_solve(ham, & ini_re, & ini_im, & ray, r,
1043 k0, & xx, & yy, & zz));
1044 }
1045 /// Finds ray with starting point r0, p0 (and prepares ray data for mglQO2d)
1046 MglData mglRay(string ham, MglPoint r0, MglPoint p0, mreal dt = 0.1, mreal tmax = 10)
1047 {
1048 return MglData(true, mgl_ray_trace(ham, r0.x, r0.y, r0.z, p0.x, p0.y, p0.z, dt,
1049 tmax));
1050 }
1051
1052 /// Saves result of ODE solving (|u|^2) for "Hamiltonian" ham with initial conditions ini
1053 MglData mglODE(string df, string var, in MglDataA* ini, mreal dt = 0.1,
1054 mreal tmax = 10)
1055 {
1056 return MglData(true, mgl_ode_solve_str(df, var, & ini, dt, tmax));
1057 }
1058 /// Calculate Jacobian determinant for D{x(u,v), y(u,v)} = dx/du*dy/dv-dx/dv*dy/du
1059 MglData mglJacobian(in MglDataA* x, in MglDataA* y)
1060 {
1061 return MglData(true, mgl_jacobian_2d( & x, & y));
1062 }
1063 /// Calculate Jacobian determinant for D{x(u,v,w), y(u,v,w), z(u,v,w)}
1064 MglData mglJacobian(in MglDataA* x, in MglDataA* y, in MglDataA* z)
1065 {
1066 return MglData(true, mgl_jacobian_3d( & x, & y, & z));
1067 }
1068 /// Do something like Delone triangulation
1069 MglData mglTriangulation(in MglDataA* x, in MglDataA* y, in MglDataA* z)
1070 {
1071 return MglData(true, mgl_triangulation_3d( & x, & y, & z));
1072 }
1073 MglData mglTriangulation(in MglDataA* x, in MglDataA* y)
1074 {
1075 return MglData(true, mgl_triangulation_2d( & x, & y));
1076 }
1077 //-----------------------------------------------------------------------------
1078 /// Get sub-array of the data with given fixed indexes
1079 MglData mglSubData(in MglDataA* dat, long xx, long yy = - 1, long zz = - 1)
1080 {
1081 return MglData(true, mgl_data_subdata( & dat, xx, yy, zz));
1082 }
1083 MglData mglSubData(in MglDataA* dat, in MglDataA* xx, in MglDataA* yy,
1084 in MglDataA* zz)
1085 {
1086 return MglData(true, mgl_data_subdata_ext( & dat, & xx, & yy, & zz));
1087 }
1088 MglData mglSubData(in MglDataA* dat, in MglDataA* xx, in MglDataA* yy)
1089 {
1090 return MglData(true, mgl_data_subdata_ext( & dat, & xx, & yy, 0));
1091 }
1092 MglData mglSubData(in MglDataA* dat, in MglDataA* xx)
1093 {
1094 return MglData(true, mgl_data_subdata_ext( & dat, & xx, 0, 0));
1095 }
1096 //-----------------------------------------------------------------------------
1097 /// Prepare coefficients for global spline interpolation
1098 MglData mglGSplineInit(in MglDataA* xdat, in MglDataA* ydat)
1099 {
1100 return MglData(true, mgl_gspline_init(*xdat, & ydat));
1101 }
1102 /// Evaluate global spline (and its derivatives d1, d2 if not NULL) using prepared coefficients \a coef
1103 mreal mglGSpline(in MglDataA* coef, mreal dx, mreal * d1 = 0, mreal * d2 = 0)
1104 {
1105 return mgl_gspline( & coef, dx, d1, d2);
1106 }
1107 //-----------------------------------------------------------------------------
1108 /// Wrapper class for expression evaluating
1109 class MglExpr
1110 {
1111 HMEX ex;
1112
1113 // copying is not allowed
1114
1115 this(string expr)
1116 {
1117 ex = mgl_create_expr(expr.toStringz);
1118 }
1119
1120 static if(HaveRval)
1121 {
1122 this(MglExpr** d)
1123 {
1124 ex=d.ex;
1125 d.ex = 0;
1126 }
1127 }
1128
1129 ~this()
1130 {
1131 mgl_delete_expr(ex);
1132 }
1133
1134 /// Return value of expression for given x,y,z variables
1135 double eval(double x, double y = 0, double z = 0)
1136 {
1137 return mgl_expr_eval(ex, x, y, z);
1138 }
1139
1140 /// Return value of expression differentiation over variable dir for given x,y,z variables
1141 double diff(char dir, double x, double y = 0, double z = 0)
1142 {
1143 return mgl_expr_diff(ex, dir, x, y, z);
1144 }
1145
1146 static if(!SWIG)
1147 {
1148 // Return value of expression for given variables
1149 double Eval(mreal var[26])
1150 {
1151 return mgl_expr_eval_v(ex, var);
1152 }
1153
1154 /// Return value of expression differentiation over variable dir for given variables
1155 double Diff(char dir, mreal var[26])
1156 {
1157 return mgl_expr_diff_v(ex, dir, var);
1158 }
1159 }
1160 }
1161
1162 // Class which presents variable as data array
1163 class MglDataV : MglDataA
1164 {
1165 long nx; ///< number of points in 1st dimensions ('x' dimension)
1166 long ny; ///< number of points in 2nd dimensions ('y' dimension)
1167 long nz; ///< number of points in 3d dimensions ('z' dimension)
1168 mreal di, dj, dk, a0;
1169
1170 this(long xx = 1, long yy = 1, long zz = 1, mreal x1 = 0, mreal x2 = mglNaN, char dir = 'x')
1171 {
1172 this.nx=xx;
1173 this.ny=ny;
1174 this.nz=nz;
1175 fill(x1, x2, dir);
1176 }
1177
1178 this(MglDataV d)
1179 {
1180 this.nx=d.nx;
1181 this.ny=d.ny;
1182 this.nz=d.nz;
1183 this.di=d.di;
1184 this.dj=d.dj;
1185 this.dk=d.dk;
1186 this.a0=d.ao;
1187 }
1188
1189 static if(HaveRval)
1190 {
1191 this(MglDataV d)
1192 {
1193 this.nx=d.nx;
1194 this.ny=d.ny;
1195 this.nz=d.nz;
1196 this.di=d.di;
1197 this.dj=d.dj;
1198 this.dk=d.dk;
1199 this.a0=d.ao;
1200 s = d.s;
1201 temp = d.temp;
1202 func = d.func;
1203 o = d.o;
1204 d.func = 0;
1205 }
1206 }
1207
1208 /// Get sizes
1209 long getNx() const
1210 {
1211 return nx;
1212 }
1213
1214 long getNy() const
1215 {
1216 return ny;
1217 }
1218
1219 long getNz() const
1220 {
1221 return nz;
1222 }
1223
1224 /// create or recreate the array with specified size and fill it by zero
1225 void create(long mx, long my = 1, long mz = 1)
1226 {
1227 di = mx > 1 ? di * (nx - 1) / (mx - 1) : 0;
1228 dj = my > 1 ? dj * (ny - 1) / (my - 1) : 0;
1229 dk = mz > 1 ? dk * (nz - 1) / (mz - 1) : 0;
1230 nx = mx;
1231 ny = my;
1232 nz = mz;
1233 }
1234
1235 /// For going throw all elements
1236 void all()
1237 {
1238 di = dj = dk = 1;
1239 a0 = 0;
1240 }
1241
1242 /// Equidistantly fill the data to range [x1,x2] in direction dir
1243 void fill(mreal x1, mreal x2 = mglNaN, char dir = 'x')
1244 {
1245 di = dj = dk = 0;
1246 a0 = x1;
1247 if (mgl_isnum(x2))
1248 {
1249 if (dir == 'x' && nx > 1)
1250 di = (x2 - x1) / (nx - 1);
1251 if (dir == 'y' && ny > 1)
1252 dj = (x2 - x1) / (ny - 1);
1253 if (dir == 'z' && nz > 1)
1254 dk = (x2 - x1) / (nz - 1);
1255 }
1256 }
1257
1258 mreal maximal() const
1259 {
1260 return a0 + mgl_max(mgl_max(di * (nx - 1), dj * (ny - 1)), mgl_max(dk * (nz - 1),
1261 0));
1262 }
1263
1264 mreal minimal() const
1265 {
1266 return a0 + mgl_min(mgl_min(di * (nx - 1), dj * (ny - 1)), mgl_min(dk * (nz - 1),
1267 0));
1268 }
1269
1270 /*
1271 /// Copy data from other MglDataV variable
1272 const MglDataV & operator = (const MglDataV & d)
1273 {
1274 nx = d.nx;
1275 ny = d.ny;
1276 nz = d.nz;
1277 a0 = d.a0;
1278 di = d.di;
1279 dj = d.dj;
1280 dk = d.dk;
1281 return d;
1282 }
1283 mreal operator = (mreal val)
1284 {
1285 di = dj = dk = 0;
1286 a0 = val;
1287 return val;
1288 }
1289 */
1290
1291 /// Get the value in given cell of the data without border checking
1292 mreal value(mreal x, mreal y, mreal z, mreal * dx = 0, mreal * dy = 0, mreal * dz = 0) const
1293 {
1294 if (dx)
1295 * dx = di;
1296 if (dy)
1297 * dy = dj;
1298 if (dz)
1299 * dz = dk;
1300 return a0 + di * x + dj * y + dk * z;
1301 }
1302 mreal v(long i, long j = 0, long k = 0) const
1303 {
1304 return a0 + di * i + dj * j + dk * k;
1305 }
1306
1307 mreal vthr(long ii) const
1308 {
1309 long i = ii % nx, j = (ii / nx) % ny, k = ii / (nx * ny);
1310 return a0 + di * i + dj * j + dk * k;
1311 }
1312
1313 // add for speeding up !!!
1314 mreal dvx(long, long = 0, long = 0) const
1315 {
1316 return di;
1317 }
1318
1319 mreal dvy(long, long = 0, long = 0) const
1320 {
1321 return dj;
1322 }
1323
1324 mreal dvz(long, long = 0, long = 0) const
1325 {
1326 return dk;
1327 }
1328 };
1329 //-----------------------------------------------------------------------------
1330 /// Class which present FFT frequency as data array
1331 class MglDataW : MglDataA
1332 {
1333 long nx; ///< number of points in 1st dimensions ('x' dimension)
1334 long ny; ///< number of points in 2nd dimensions ('y' dimension)
1335 long nz; ///< number of points in 3d dimensions ('z' dimension)
1336 mreal di, dj, dk;
1337
1338 this(long xx = 1, long yy = 1, long zz = 1, mreal dp = 0, char dir = 'x')
1339 {
1340 this.nx=xx;
1341 this.ny=yy;
1342 this.nz=zz;
1343 freq(dp, dir);
1344 }
1345
1346 this(const MglDataW d)
1347 {
1348 this.nx=d.nx;
1349 this.ny=d.ny;
1350 this.nz=d.nz;
1351 this.di=d.di;
1352 this.dj=d.dj;
1353 this.dk=d.dk;
1354 }
1355
1356 static if (HaveRval)
1357 {
1358 this(MglDataW* d)
1359 {
1360 this.nx=d.nx;
1361 this.ny=d.ny;
1362 this.nz=d.nz;
1363 this.di=d.di;
1364 this.dj=d.dj;
1365 this.dk=d.dk;
1366 s = d.s;
1367 temp = d.temp;
1368 func = d.func;
1369 o = d.o;
1370 d.func = 0;
1371 }
1372 }
1373
1374 /// Get sizes
1375 long getNx() const
1376 {
1377 return nx;
1378 }
1379
1380 long getNy() const
1381 {
1382 return ny;
1383 }
1384
1385 long getNz() const
1386 {
1387 return nz;
1388 }
1389
1390 /// create or recreate the array with specified size and fill it by zero
1391 void create(long mx, long my = 1, long mz = 1)
1392 {
1393 nx = mx;
1394 ny = my;
1395 nz = mz;
1396 }
1397
1398 /// For going throw all elements
1399 void all()
1400 {
1401 di = dj = dk = 1;
1402 }
1403
1404 /// Equidistantly fill the data to range [x1,x2] in direction dir
1405 void Freq(mreal dp, char dir = 'x')
1406 {
1407 di = dj = dk = 0;
1408 if (dir == 'x')
1409 di = dp;
1410 if (dir == 'y')
1411 dj = dp;
1412 if (dir == 'z')
1413 dk = dp;
1414 }
1415
1416 mreal maximal() const
1417 {
1418 return mgl_max(mgl_max(di * (nx - 1), dj * (ny - 1)), mgl_max(dk * (nz - 1),
1419 0));
1420 }
1421
1422 mreal minimal() const
1423 {
1424 return mgl_min(mgl_min(di * (nx - 1), dj * (ny - 1)), mgl_min(dk * (nz - 1),
1425 0));
1426 }
1427 /*
1428 /// Copy data from other MglDataV variable
1429 const MglDataW & operator = (const MglDataW & d)
1430 {
1431 nx = d.nx;
1432 ny = d.ny;
1433 nz = d.nz;
1434 di = d.di;
1435 dj = d.dj;
1436 dk = d.dk;
1437 return d;
1438 }
1439 */
1440 /// Get the value in given cell of the data without border checking
1441 mreal value(mreal x, mreal y, mreal z, mreal* dx = 0, mreal* dy = 0, mreal* dz = 0) const
1442 {
1443 if (dx)
1444 *dx = di;
1445 if (dy)
1446 *dy = dj;
1447 if (dz)
1448 *dz = dk;
1449 return di * (x < nx / 2 ? x : nx - x) + dj * (y < ny / 2 ? y : ny - y) + dk * (
1450 z < nz / 2 ? z : nz - z);
1451 }
1452
1453 mreal v(long i, long j = 0, long k = 0) const
1454 {
1455 return di * (i < nx / 2 ? i : nx - i) + dj * (j < ny / 2 ? j : ny - j) + dk * (
1456 k < nz / 2 ? k : nz - k);
1457 }
1458
1459 mreal vthr(long ii) const
1460 {
1461 long i = ii % nx, j = (ii / nx) % ny, k = ii / (nx * ny);
1462 return di * (i < nx / 2 ? i : nx - i) + dj * (j < ny / 2 ? j : ny - j) + dk * (
1463 k < nz / 2 ? k : nz - k);
1464 }
1465
1466 // add for speeding up !!!
1467 mreal dvx(long, long = 0, long = 0) const
1468 {
1469 return di;
1470 }
1471
1472 mreal dvy(long, long = 0, long = 0) const
1473 {
1474 return dj;
1475 }
1476
1477 mreal dvz(long, long = 0, long = 0) const
1478 {
1479 return dk;
1480 }
1481 }
1482
1483 // Class which presents variable as data array
1484 class MglDataF : MglDataA
1485 {
1486 long nx; ///< number of points in 1st dimensions ('x' dimension)
1487 long ny; ///< number of points in 2nd dimensions ('y' dimension)
1488 long nz; ///< number of points in 3d dimensions ('z' dimension)
1489 string str; ///< function as string
1490 MglPoint v1, v2; ///< ranges for coordinates
1491 HMEX ex; ///< parsed variant
1492 mreal dx, dy, dz;
1493 void setD()
1494 {
1495 dx = nx > 1 ? (v2.x - v1.x) / (nx - 1) : 0;
1496 dy = ny > 1 ? (v2.y - v1.y) / (ny - 1) : 0;
1497 dz = nz > 1 ? (v2.z - v1.z) / (nz - 1) : 0;
1498 }
1499
1500 mreal function(mreal i, mreal j, mreal k, void * par) func;
1501 void* par;
1502
1503 this(long xx = 1, long yy = 1, long zz = 1)
1504 {
1505 this.nx=xx;
1506 this.ny=yy;
1507 this.nz=zz;
1508 this.dfunc=0;
1509 this.par=0;
1510 ex = 0;
1511 v2 = MglPoint(1, 1, 1);
1512 setD();
1513 }
1514
1515 this(MglDataF d)
1516 {
1517 this.nx=d.nx;
1518 this.ny=d.ny;
1519 this.nz=d.nz;
1520 this.str=d.str;
1521 this.v1=d.v1;
1522 this.v2=d.v2;
1523 this.dx=d.dx;
1524 this.dy=d.dy;
1525 this.dz=d.dz;
1526 this.dfunc=d.dfunc;
1527 this.par=d.par;
1528 ex = mgl_create_expr(str.c_str());
1529 }
1530
1531 static if(HaveRval)
1532 {
1533 this(MglDataF d)
1534 {
1535 this.nx=d.nx;
1536 this.ny=d.ny;
1537 this.nz=d.nz;
1538 this.str=d.str;
1539 this.v1=d.v1;
1540 this.v2=d.v2;
1541 this.dx=d.dx;
1542 this.dy=d.dy;
1543 this.dz=d.dz;
1544 this.dfunc=d.dfunc;
1545 this.par=d.par;
1546 s = d.s;
1547 temp = d.temp;
1548 func = d.func;
1549 o = d.o;
1550 d.ex = 0;
1551 d.func = 0;
1552 }
1553 }
1554
1555 ~this()
1556 {
1557 mgl_delete_expr(ex);
1558 }
1559
1560 /// Get sizes
1561 long getNx() const
1562 {
1563 return nx;
1564 }
1565
1566 long getNy() const
1567 {
1568 return ny;
1569 }
1570
1571 long getNz() const
1572 {
1573 return nz;
1574 }
1575
1576 /// create or recreate the array with specified size and fill it by zero
1577 void create(long mx, long my = 1, long mz = 1)
1578 {
1579 nx = mx;
1580 ny = my;
1581 nz = mz;
1582 setD();
1583 }
1584
1585 void setRanges(MglPoint p1, MglPoint p2)
1586 {
1587 v1 = p1;
1588 v2 = p2;
1589 setD();
1590 }
1591
1592 /// set formula to be used as dfunction
1593 void setFormula(string eq)
1594 {
1595 mgl_delete_expr(ex);
1596 dfunc = 0;
1597 par = 0;
1598 if (eq && *eq)
1599 {
1600 ex = mgl_create_expr(eq);
1601 str = eq;
1602 }
1603 else
1604 {
1605 ex = 0;
1606 str = "";
1607 }
1608 }
1609
1610 /// set dfunction and coordinates range [r1,r2]
1611 void setFunc(mreal function(mreal, mreal, mreal, void * ) f, void * p = NULL)
1612 {
1613 mgl_delete_expr(ex);
1614 ex = 0;
1615 dfunc = f;
1616 par = p;
1617 }
1618
1619 mreal value(mreal i, mreal j = 0, mreal k = 0, mreal* di = 0, mreal* dj = 0, mreal* dk = 0) const
1620 {
1621 mreal res = 0, x = v1.x + dx * i, y = v1.y + dy * j, z = v1.z + dz * k;
1622 if (di)
1623 *di = 0;
1624 if (dj)
1625 *dj = 0;
1626 if (dk)
1627 *dk = 0;
1628 if (dfunc)
1629 {
1630 res = dfunc(x, y, z, par);
1631 if (di)
1632 *di = dfunc(x + dx, y, z, par) - res;
1633 if (dj)
1634 *dj = dfunc(x, y + dy, z, par) - res;
1635 if (dk)
1636 *dk = dfunc(x, y, z + dz, par) - res;
1637 }
1638 else if (ex)
1639 {
1640 if (di)
1641 *di = mgl_expr_diff(ex, 'x', x, y, z) * dx;
1642 if (dj)
1643 *dj = mgl_expr_diff(ex, 'y', x, y, z) * dy;
1644 if (dk)
1645 *dk = mgl_expr_diff(ex, 'z', x, y, z) * dz;
1646 res = mgl_expr_eval(ex, x, y, z);
1647 }
1648 return res;
1649 }
1650 /*
1651 /// Copy data from other MglDataV variable
1652 const MglDataF & operator = (const MglDataF & d)
1653 {
1654 nx = d.nx;
1655 ny = d.ny;
1656 nz = d.nz;
1657 v1 = d.v1;
1658 v2 = d.v2;
1659 setD();
1660 str = d.str;
1661 ex = mgl_create_expr(str.c_str());
1662 dfunc = d.dfunc;
1663 par = d.par;
1664 return d;
1665 }
1666 */
1667 /// Get the value in given cell of the data without border checking
1668 mreal v(long i, long j = 0, long k = 0) const
1669 {
1670 mreal res = 0, x = v1.x + dx * i, y = v1.y + dy * j, z = v1.z + dz * k;
1671 if (dfunc)
1672 res = dfunc(x, y, z, par);
1673 else if (ex)
1674 res = mgl_expr_eval(ex, x, y, z);
1675 return res;
1676 }
1677
1678 mreal vthr(long i) const
1679 {
1680 mreal res = 0, x = v1.x + dx * (i % nx), y = v1.y + dy * ((i / nx) % ny),
1681 z = v1.z + dz * (i / (nx * ny));
1682 if (dfunc)
1683 res = dfunc(x, y, z, par);
1684 else if (ex)
1685 res = mgl_expr_eval(ex, x, y, z);
1686 return res;
1687 }
1688
1689 // add for speeding up !!!
1690 mreal dvx(long i, long j = 0, long k = 0) const
1691 {
1692 mreal res = 0, x = v1.x + dx * i, y = v1.y + dy * j, z = v1.z + dz * k;
1693 if (dfunc)
1694 res = dfunc(x + dx, y, z, par) - dfunc(x, y, z, par);
1695 else if (ex)
1696 res = mgl_expr_eval(ex, x + dx, y, z) - mgl_expr_eval(ex, x, y, z);
1697 return res;
1698 }
1699
1700 mreal dvy(long i, long j = 0, long k = 0) const
1701 {
1702 mreal res = 0, x = v1.x + dx * i, y = v1.y + dy * j, z = v1.z + dz * k;
1703 if (dfunc)
1704 res = dfunc(x, y + dy, z, par) - dfunc(x, y, z, par);
1705 else if (ex)
1706 res = mgl_expr_eval(ex, x, y + dy, z) - mgl_expr_eval(ex, x, y, z);
1707 return res;
1708 }
1709
1710 mreal dvz(long i, long j = 0, long k = 0) const
1711 {
1712 mreal res = 0, x = v1.x + dx * i, y = v1.y + dy * j, z = v1.z + dz * k;
1713 if (dfunc)
1714 res = dfunc(x, y, z + dz, par) - dfunc(x, y, z, par);
1715 else if (ex)
1716 res = mgl_expr_eval(ex, x, y, z + dz) - mgl_expr_eval(ex, x, y, z);
1717 return res;
1718 }
1719 }
1720
1721 // Class which present variable as data array
1722 class MglDataT : MglDataA
1723 {
1724 MglDataA* dat;
1725 long ind;
1726
1727 this(const MglDataT d)
1728 {
1729 this.dat=d.dat;
1730 this.ind=d.ind;
1731 s = d.s;
1732 }
1733
1734 this(in MglDataA* d, long col = 0)
1735 {
1736 this.dat=d;
1737 this.ind=col;
1738 }
1739
1740 static if(HaveRval)
1741 {
1742 this(MglDataT* d)
1743 {
1744 this.dat=d.dat;
1745 this.ind=d.ind;
1746 s = d.s;
1747 temp = d.temp;
1748 func = d.func;
1749 o = d.o;
1750 d.func = 0;
1751 }
1752 }
1753
1754 ~this()
1755 {
1756 }
1757
1758 /// Get sizes
1759 long getNx() const
1760 {
1761 return dat.getNy();
1762 }
1763
1764 long getNy() const
1765 {
1766 return dat.getNz();
1767 }
1768
1769 long getNz() const
1770 {
1771 return 1;
1772 }
1773
1774 mreal maximal() const
1775 {
1776 return mglSubData(dat, ind).maximal();
1777 }
1778
1779 mreal minimal() const
1780 {
1781 return mglSubData(dat, ind).minimal();
1782 }
1783
1784 void setInd(long i, const wchar_t* name)
1785 {
1786 ind = i;
1787 s = name;
1788 }
1789
1790 void setInd(long i, wchar_t name)
1791 {
1792 ind = i;
1793 s = name;
1794 }
1795
1796 /// Get the value in given cell of the data without border checking
1797 mreal v(long i, long j = 0, long = 0) const
1798 {
1799 return dat.v(ind, i, j);
1800 }
1801
1802 mreal vthr(long i) const
1803 {
1804 return dat.vthr(ind + dat.getNx() * i);
1805 }
1806
1807 // add for speeding up !!!
1808 mreal dvx(long i, long j = 0, long = 0) const
1809 {
1810 return dat.dvy(ind, i, j);
1811 }
1812
1813 mreal dvy(long i, long j = 0, long = 0) const
1814 {
1815 return dat.dvz(ind, i, j);
1816 }
1817
1818 mreal dvz(long, long = 0, long = 0) const
1819 {
1820 return 0;
1821 }
1822 }
1823
1824 class MglDataR : MglDataA
1825 {
1826 MglDataA* dat;
1827 long ind;
1828
1829 this(const MglDataR d)
1830 {
1831 this.dat=d.dat;
1832 this.ind=d.ind;
1833 s=d.s;
1834 }
1835
1836 this(in MglDataA d, long row = 0)
1837 {
1838 this.dat=d;
1839 this.ind=row;
1840 }
1841
1842 static if(HaveRval)
1843 {
1844 this(MglDataR* d)
1845 {
1846 this.dat=d.dat;
1847 this.ind=d.ind;
1848 s = d.s;
1849 temp = d.temp;
1850 func = d.func;
1851 o = d.o;
1852 d.func = 0;
1853 }
1854 }
1855 ~this()
1856 {
1857
1858 }
1859
1860 /// Get sizes
1861 long getNx() const
1862 {
1863 return dat.getNx();
1864 }
1865
1866 long getNy() const
1867 {
1868 return 1;
1869 }
1870
1871 long getNz() const
1872 {
1873 return 1;
1874 }
1875
1876 mreal maximal() const
1877 {
1878 return mglSubData(dat, -1, ind).maximal();
1879 }
1880
1881 mreal minimal() const
1882 {
1883 return mglSubData(dat, -1, ind).minimal();
1884 }
1885
1886 void setInd(long i, const wchar_t* name)
1887 {
1888 ind = i;
1889 s = name;
1890 }
1891
1892 void setInd(long i, wchar_t name)
1893 {
1894 ind = i;
1895 s = name;
1896 }
1897
1898 /// Get the value in given cell of the data without border checking
1899 mreal v(long i, long j= 0, long k= 0) const
1900 {
1901 return dat.v(i, ind, 0);
1902 }
1903
1904 mreal vthr(long i) const
1905 {
1906 return dat.vthr(i + dat.getNx() * ind);
1907 }
1908
1909 // add for speeding up !!!
1910 mreal dvx(long i, long j = 0, long k= 0) const
1911 {
1912 return dat.dvx(i, ind, 0);
1913 }
1914
1915 mreal dvy(long i, long j = 0, long k= 0) const
1916 {
1917 return 0;
1918 }
1919
1920 mreal dvz(long i, long j= 0, long k = 0) const
1921 {
1922 return 0;
1923 }
1924 }
1925
1926
1927 auto mgl2()
1928 {
1929 return mreal(2);
1930 }
1931
1932 auto mgl3()
1933 {
1934 return mreal(3);
1935 }
1936
1937 auto mgl4()
1938 {
1939 return mreal(4);
1940 }
1941
1942
1943 /// Class for working with complex data array
1944 class MglDataC:MglDataA
1945 {
1946 //public : using MglDataA : : Momentum;
1947 long nx; ///< number of points in 1st dimensions ('x' dimension)
1948 long ny; ///< number of points in 2nd dimensions ('y' dimension)
1949 long nz; ///< number of points in 3d dimensions ('z' dimension)
1950 dual* a; ///< data array
1951 string id; ///< column (or slice) names
1952 bool useLink; ///< use external data (i.e. don't free it)
1953
1954 /// Initiate by other MglDataC variable
1955 this(in MglDataC* d)
1956 {
1957 a = 0;
1958 mgl_datac_set(this, & d);
1959 } // NOTE: must be constructor for MglDataC& to exclude copy one
1960
1961 this(in MglDataA* d)
1962 {
1963 a = 0;
1964 mgl_datac_set(this, & d);
1965 }
1966
1967 static if(HaveRval)
1968 {
1969 this(MglDataC** d)
1970 {
1971 this.nx=d.nx;
1972 this.ny=d.ny;
1973 this.nz=d.nz;
1974 this.a=d.a;
1975 this.id=d.id;
1976 this.useLink=d.useLink;
1977 //this.s = d.s;
1978 //this.temp = d.temp;
1979 func = d.func;
1980 //this.o = d.o;
1981 d.a = 0;
1982 d.func = 0;
1983 }
1984 }
1985
1986 this(in MglDataA* re, in MglDataA* im)
1987 {
1988 a = 0;
1989 mgl_datac_set_ri(this, & re, *im);
1990 }
1991
1992 this(HCDT d)
1993 {
1994 a = 0;
1995 mgl_datac_set(this, d);
1996 }
1997
1998 this(HCDT re, HCDT im)
1999 {
2000 a = 0;
2001 mgl_datac_set_ri(this, re, im);
2002 }
2003
2004 this(bool, MglDataC * d) // NOTE: Variable d will be deleted!!!
2005 {
2006 if (d)
2007 {
2008 nx = d.nx;
2009 ny = d.ny;
2010 nz = d.nz;
2011 a = d.a;
2012 d.a = 0;
2013 temp = d.temp;
2014 func = d.func;
2015 o = d.o;
2016 s = d.s;
2017 id = d.id;
2018 useLink = d.useLink;
2019 delete d;
2020 }
2021 else
2022 {
2023 a = 0;
2024 Create(1);
2025 }
2026 }
2027
2028 /// Initiate by flat array
2029 this(int size, const dual * d)
2030 {
2031 a = 0;
2032 set(d, size);
2033 }
2034 this(int rows, int cols, const dual * d)
2035 {
2036 a = 0;
2037 set(d, cols, rows);
2038 }
2039 this(int size, const double * d)
2040 {
2041 a = 0;
2042 set(d, size);
2043 }
2044 this(int rows, int cols, const double * d)
2045 {
2046 a = 0;
2047 set(d, cols, rows);
2048 }
2049 this(int size, const float * d)
2050 {
2051 a = 0;
2052 set(d, size);
2053 }
2054 this(int rows, int cols, const float * d)
2055 {
2056 a = 0;
2057 set(d, cols, rows);
2058 }
2059 this(in dual * d, int size)
2060 {
2061 a = 0;
2062 set(d, size);
2063 }
2064 this(in dual * d, int rows, int cols)
2065 {
2066 a = 0;
2067 set(d, cols, rows);
2068 }
2069 this(in double * d, int size)
2070 {
2071 a = 0;
2072 set(d, size);
2073 }
2074 this(in double * d, int rows, int cols)
2075 {
2076 a = 0;
2077 set(d, cols, rows);
2078 }
2079 this(in float * d, int size)
2080 {
2081 a = 0;
2082 set(d, size);
2083 }
2084 this(in float * d, int rows, int cols)
2085 {
2086 a = 0;
2087 set(d, cols, rows);
2088 }
2089 /// read data from file
2090 this(string fname)
2091 {
2092 a = 0;
2093 read(fname);
2094 }
2095 /// Allocate the memory for data array and initialize it zero
2096 this(long xx = 1, long yy = 1, long zz = 1)
2097 {
2098 a = 0;
2099 Create(xx, yy, zz);
2100 }
2101 /// Delete the array
2102 ~this()
2103 {
2104 //if (!useLink && a)
2105 // delete[] a;
2106 }
2107
2108 dual getVal(long i, long j = 0, long k = 0) const
2109 {
2110 return mgl_datac_get_value(this, i, j, k);
2111 }
2112
2113 void setVal(dual f, long i, long j = 0, long k = 0)
2114 {
2115 mgl_datac_set_value(this, f, i, j, k);
2116 }
2117
2118 /// get sizes
2119 long getNx() const
2120 {
2121 return nx;
2122 }
2123
2124 long getNy() const
2125 {
2126 return ny;
2127 }
2128
2129 long getNz() const
2130 {
2131 return nz;
2132 }
2133
2134 /// Link external data array (don't delete it at exit)
2135 void link(dual* A, long NX, long NY = 1, long NZ = 1)
2136 {
2137 mgl_datac_link(this, A, NX, NY, NZ);
2138 }
2139
2140 void link(MglDataC* d)
2141 {
2142 Link(d.a, d.nx, d.ny, d.nz);
2143 }
2144 /// Allocate memory and copy the data from the gsl_vector
2145 void set(gsl_vector* m)
2146 {
2147 mgl_datac_set_vector(this, m);
2148 }
2149
2150 /// Allocate memory and copy the data from the gsl_matrix
2151 void set(gsl_matrix* m)
2152 {
2153 mgl_datac_set_matrix(this, m);
2154 }
2155
2156 /// Allocate memory and copy the data from the (float *) array
2157 void set(const float* A, long NX, long NY = 1, long NZ = 1)
2158 {
2159 mgl_datac_set_float(this, A, NX, NY, NZ);
2160 }
2161
2162 /// Allocate memory and copy the data from the (double *) array
2163 void set(const double* A, long NX, long NY = 1, long NZ = 1)
2164 {
2165 mgl_datac_set_double(this, A, NX, NY, NZ);
2166 }
2167
2168 /// Allocate memory and copy the data from the (complex *) array
2169 void set(const dual* A, long NX, long NY = 1, long NZ = 1)
2170 {
2171 mgl_datac_set_complex(this, A, NX, NY, NZ);
2172 }
2173
2174 /// Allocate memory and scanf the data from the string
2175 void set(string str, long NX, long NY = 1, long NZ = 1)
2176 {
2177 mgl_datac_set_values(this, str.toStringz, NX, NY, NZ);
2178 }
2179
2180 /// Import data from abstract type
2181 void set(HCDT dat)
2182 {
2183 mgl_datac_set(this, dat);
2184 }
2185
2186 void set(in MglDataA* dat)
2187 {
2188 mgl_datac_set(this, & dat);
2189 }
2190 void set(in MglDataA* re, in MglDataA* im)
2191 {
2192 mgl_datac_set_ri(this, & re, & im);
2193 }
2194 void set(HCDT re, HCDT im)
2195 {
2196 mgl_datac_set_ri(this, re, im);
2197 }
2198
2199 void setAmpl(in MglDataA* ampl, in MglDataA* phase)
2200 {
2201 mgl_datac_set_ap(this, & ampl, & phase);
2202 }
2203 /// Allocate memory and copy data from std::vector<T>
2204 void set(int[] d)
2205 {
2206 if (d.length < 1)
2207 return;
2208 Create(d.length());
2209 foreach(i;0..nx)
2210 a[i] = d[i];
2211 }
2212 void set(float[] d)
2213 {
2214 if (d.length < 1)
2215 return;
2216 create(d.length());
2217 foreach(i;0..nx)
2218 a[i] = d[i];
2219 }
2220 void set(double[] d)
2221 {
2222 if (d.length() < 1)
2223 return;
2224 Create(d.length);
2225 foreach(i;0..nx)
2226 a[i] = d[i];
2227 }
2228
2229 void set(dual[] d)
2230 {
2231 if (d.length() < 1)
2232 return;
2233 create(d.length);
2234 foreach(i;0..nx)
2235 a[i] = d[i];
2236 }
2237
2238 /// Create or recreate the array with specified size and fill it by zero
2239 void create(long mx, long my = 1, long mz = 1)
2240 {
2241 mgl_datac_create(this, mx, my, mz);
2242 }
2243
2244 /// Rearange data dimensions
2245 void rearrange(long mx, long my = 0, long mz = 0)
2246 {
2247 mgl_datac_rearrange(this, mx, my, mz);
2248 }
2249
2250 /// Transpose dimensions of the data (generalization of Transpose)
2251 void transpose(string dim = "yx")
2252 {
2253 mgl_datac_transpose(this, dim.toStringz);
2254 }
2255
2256 /// Extend data dimensions
2257 void extend(long n1, long n2 = 0)
2258 {
2259 mgl_datac_extend(this, n1, n2);
2260 }
2261
2262 /// Reduce size of the data
2263 void squeeze(long rx, long ry = 1, long rz = 1, bool smooth = false)
2264 {
2265 mgl_datac_squeeze(this, rx, ry, rz, smooth);
2266 }
2267
2268 /// Crop the data
2269 void crop(long n1, long n2, char dir = 'x')
2270 {
2271 mgl_datac_crop(this, n1, n2, dir);
2272 }
2273
2274 /// Insert data
2275 void insert(char dir, long at = 0, long num = 1)
2276 {
2277 mgl_datac_insert(this, dir, at, num);
2278 }
2279
2280 /// Delete data
2281 void deleteData(char dir, long at = 0, long num = 1)
2282 {
2283 mgl_datac_delete(this, dir, at, num);
2284 }
2285
2286 /// Join with another data array
2287 void join(in MglDataA* d)
2288 {
2289 mgl_datac_join(this, & d);
2290 }
2291
2292 /// Modify the data by specified formula
2293 void modify(string eq, long dim = 0)
2294 {
2295 mgl_datac_modify(this, eq, dim);
2296 }
2297
2298 /// Modify the data by specified formula
2299 void modify(const char * eq, in MglDataA* vdat, in MglDataA* wdat)
2300 {
2301 mgl_datac_modify_vw(this, eq, & vdat, & wdat);
2302 }
2303 /// Modify the data by specified formula
2304 void modify(const char * eq, in MglDataA* vdat)
2305 {
2306 mgl_datac_modify_vw(this, eq, & vdat, 0);
2307 }
2308 /// Modify the data by specified formula assuming x,y,z in range [r1,r2]
2309 void fill(mglBase* gr, string eq, string opt = "")
2310 {
2311 mgl_datac_fill_eq(gr, this, eq, 0, 0, opt);
2312 }
2313
2314 void fill(mglBase * gr, const char * eq, in MglDataA* vdat, string opt = "")
2315 {
2316 mgl_datac_fill_eq(gr, this, eq, & vdat, 0, opt.toStringz);
2317 }
2318
2319 void Fill(mglBase * gr, const char * eq, in MglDataA* vdat, in MglDataA* wdat,string opt = "")
2320 {
2321 mgl_datac_fill_eq(gr, this, eq, & vdat, & wdat, opt.toStringz);
2322 }
2323 /// Equidistantly fill the data to range [x1,x2] in direction dir
2324 void fill(dual x1, dual x2 = mglNaN, char dir = 'x')
2325 {
2326 mgl_datac_fill(this, x1, x2, dir);
2327 }
2328
2329 /// Put value to data element(s)
2330 void put(dual val, long i = -1, long j = -1, long k = -1)
2331 {
2332 mgl_datac_put_val(this, val, i, j, k);
2333 }
2334
2335 /// Put array to data element(s)
2336 void put(in MglDataA* dat, long i = - 1, long j = - 1, long k = - 1)
2337 {
2338 mgl_datac_put_dat(this, & dat, i, j, k);
2339 }
2340
2341 /// set names for columns (slices)
2342 void setColumnId(string ids)
2343 {
2344 mgl_datac_set_id(this, ids);
2345 }
2346
2347 /// Make new id
2348 void newId()
2349 {
2350 id.clear();
2351 }
2352
2353 /// read data from tab-separated text file with auto determining size
2354 bool read(string fname)
2355 {
2356 return mgl_datac_read(this, fname.toStringz);
2357 }
2358
2359 /// read data from text file with specifeid size
2360 bool read(string fname, long mx, long my = 1, long mz = 1)
2361 {
2362 return mgl_datac_read_dim(this, fname.toStringz, mx, my, mz);
2363 }
2364
2365 /// save whole data array (for ns=-1) or only ns-th slice to text file
2366 void save(string fname, long ns = -1) const
2367 {
2368 mgl_datac_save(this, fname.toStringz, ns);
2369 }
2370
2371 /// read data from tab-separated text files with auto determining size which filenames are result of sprintf(fname,templ,t) where t=from:step:to
2372 bool readRange(string templ, double from, double to,
2373 double step = 1, bool as_slice = false)
2374 {
2375 return mgl_datac_read_range(this, templ.toStringz, from, to, step, as_slice);
2376 }
2377
2378 /// read data from tab-separated text files with auto determining size which filenames are satisfied to template (like "t_*.dat")
2379 bool readAll(string templ, bool as_slice = false)
2380 {
2381 return mgl_datac_read_all(this, templ.toStringz, as_slice);
2382 }
2383
2384 /// read data from text file with size specified at beginning of the file
2385 bool readMat(string fname, long dim = 2)
2386 {
2387 return mgl_datac_read_mat(this, fname.toStringz, dim);
2388 }
2389
2390 /// read data array from HDF file (parse HDF4 and HDF5 files)
2391 int readHDF(string fname, ubyte[] data)
2392 {
2393 return mgl_datac_read_hdf(this, fname, data.ptr);
2394 }
2395
2396 /// save data to HDF file
2397 void saveHDF(string fname, ubyte[] data, bool rewrite = false) const
2398 {
2399 mgl_datac_save_hdf(this, fname, data.ptr, rewrite);
2400 }
2401
2402 /// get real part of data values
2403 MglData getReal() const
2404 {
2405 return MglData(true, mgl_datac_real(this));
2406 }
2407 /// get imaginary part of data values
2408 MglData getImag() const
2409 {
2410 return MglData(true, mgl_datac_imag(this));
2411 }
2412 /// get absolute value of data values
2413 MglData getAbs() const
2414 {
2415 return MglData(true, mgl_datac_abs(this));
2416 }
2417 /// get argument of data values
2418 MglData getArg() const
2419 {
2420 return MglData(true, mgl_datac_arg(this));
2421 }
2422
2423 /// get column (or slice) of the data filled by formulas of named columns
2424 MglDataC getColumn(string eq) const
2425 {
2426 return MglDataC(true, mgl_datac_column(this, eq.toStringz));
2427 }
2428
2429 /// get momentum (1D-array) of data along direction 'dir'. String looks like "x1" for median in x-direction, "x2" for width in x-dir and so on.
2430 MglDataC getMomentum(char dir, string how) const
2431 {
2432 return MglDataC(true, mgl_datac_momentum(this, dir, how.toStringz));
2433 }
2434 /// get sub-array of the data with given fixed indexes
2435 MglDataC subData(long xx, long yy = - 1, long zz = - 1) const
2436 {
2437 return MglDataC(true, mgl_datac_subdata(this, xx, yy, zz));
2438 }
2439 MglDataC subData(in MglDataA* xx, in MglDataA* yy, in MglDataA* zz) const
2440 {
2441 return MglDataC(true, mgl_datac_subdata_ext(this, & xx, & yy, & zz));
2442 }
2443 MglDataC subData(in MglDataA* xx, in MglDataA* yy) const
2444 {
2445 return MglDataC(true, mgl_datac_subdata_ext(this, & xx, & yy, 0));
2446 }
2447 MglDataC subData(in MglDataA* xx) const
2448 {
2449 return MglDataC(true, mgl_datac_subdata_ext(this, & xx, 0, 0));
2450 }
2451 /// get trace of the data array
2452 MglDataC trace() const
2453 {
2454 return MglDataC(true, mgl_datac_trace(this));
2455 }
2456 /// get array which is result of summation in given direction or directions
2457 MglDataC sum(string dir) const
2458 {
2459 return MglDataC(true, mgl_datac_sum(this, dir.toStringz));
2460 }
2461 /// get the data which is direct multiplication (like, d[i,j] = this[i]*a[j] and so on)
2462 MglDataC combine(in MglDataA* dat) const
2463 {
2464 return MglDataC(true, mgl_datac_combine(this, & dat));
2465 }
2466 /// Resize the data to new size of box [x1,x2]*[y1,y2]*[z1,z2]
2467 MglDataC resize(long mx, long my = 1, long mz = 1, mreal x1 = 0,
2468 mreal x2 = 1, mreal y1 = 0, mreal y2 = 1, mreal z1 = 0, mreal z2 = 1) const
2469 {
2470 return MglDataC(true, mgl_datac_resize_box(this, mx, my, mz, x1, x2, y1, y2,
2471 z1, z2));
2472 }
2473 /// get array which values is result of interpolation this for coordinates from other arrays
2474 MglDataC evaluate(const MglData* idat, bool norm = true) const
2475 {
2476 return MglDataC(true, mgl_datac_evaluate(this, & idat, 0, 0, norm));
2477 }
2478 MglDataC evaluate(const MglData* idat, const MglData* jdat, bool norm = true) const
2479 {
2480 return MglDataC(true, mgl_datac_evaluate(this, & idat, & jdat, 0, norm));
2481 }
2482 MglDataC evaluate(const MglData* idat, const MglData* jdat,
2483 const MglData* kdat, bool norm = true) const
2484 {
2485 return MglDataC(true, mgl_datac_evaluate(this, & idat, & jdat, & kdat, norm));
2486 }
2487
2488 /// Find correlation with another data arrays
2489 MglDataC correlation(const MglData* dat, const char * dir) const
2490 {
2491 return MglDataC(true, mgl_datac_correl(this, & dat, dir));
2492 }
2493 /// Find auto correlation function
2494 MglDataC autoCorrelation(const char * dir) const
2495 {
2496 return MglDataC(true, mgl_datac_correl(this, this, dir));
2497 }
2498
2499 /// Create n-th points distribution of this data values in range [v1, v2]
2500 MglData hist(long n, mreal v1 = 0, mreal v2 = 1, long nsub = 0) const
2501 {
2502 return MglData(true, mgl_data_hist(this, n, v1, v2, nsub));
2503 }
2504 /// Create n-th points distribution of this data values in range [v1, v2] with weight w
2505 MglData hist(in MglDataA* w, long n, mreal v1 = 0, mreal v2 = 1, long nsub = 0) const
2506 {
2507 return MglData(true, mgl_data_hist_w(this, & w, n, v1, v2, nsub));
2508 }
2509 /// get array which is result of maximal values in given direction or directions
2510 MglData max(const char * dir) const
2511 {
2512 return MglData(true, mgl_data_max_dir(this, dir.toStringz));
2513 }
2514 /// get array which is result of minimal values in given direction or directions
2515 MglData min(const char * dir) const
2516 {
2517 return MglData(true, mgl_data_min_dir(this, dir.toStringz));
2518 }
2519
2520 /// Cumulative summation the data in given direction or directions
2521 void cumSum(string dir)
2522 {
2523 mgl_datac_cumsum(this, dir.toStringz);
2524 }
2525
2526 /// Integrate (cumulative summation) the data in given direction or directions
2527 void integral(string dir)
2528 {
2529 mgl_datac_integral(this, dir.toStringz);
2530 }
2531
2532 /// Differentiate the data in given direction or directions
2533 void diff(string dir)
2534 {
2535 mgl_datac_diff(this, dir.toStringz);
2536 }
2537
2538 /// Double-differentiate (like laplace operator) the data in given direction
2539 void diff2(string dir)
2540 {
2541 mgl_datac_diff2(this, dir.toStringz);
2542 }
2543
2544 /// Swap left and right part of the data in given direction (useful for fourier spectrums)
2545 void swap(string dir)
2546 {
2547 mgl_datac_swap(this, dir.toStringz);
2548 }
2549
2550 /// Roll data along direction dir by num slices
2551 void roll(char dir, long num)
2552 {
2553 mgl_datac_roll(this, dir, num);
2554 }
2555
2556 /// Mirror the data in given direction (useful for fourier spectrums)
2557 void mirror(string dir)
2558 {
2559 mgl_datac_mirror(this, dir.toStringz);
2560 }
2561
2562 /// Smooth the data on specified direction or directions
2563 void smooth(string dirs = "xyz", mreal delta = 0)
2564 {
2565 mgl_datac_smooth(this, dirs, delta);
2566 }
2567
2568 /// Hankel transform
2569 void hankel(string dir)
2570 {
2571 mgl_datac_hankel(this, dir.toStringz);
2572 }
2573
2574 /// Fourier transform
2575 void fft(string dir)
2576 {
2577 mgl_datac_fft(this, dir.toStringz);
2578 }
2579
2580 /// Calculate one step of diffraction by finite-difference method with parameter q
2581 void diffraction(string how, mreal q)
2582 {
2583 mgl_datac_diffr(this, how, q);
2584 }
2585
2586 /// Interpolate by cubic spline the data to given point x=[0...nx-1], y=[0...ny-1], z=[0...nz-1]
2587 dual spline(mreal x, mreal y = 0, mreal z = 0) const
2588 {
2589 return mgl_datac_spline(this, x, y, z);
2590 }
2591 /// Interpolate by cubic spline the data to given point x,\a y,\a z which normalized in range [0, 1]
2592 dual spline1(mreal x, mreal y = 0, mreal z = 0) const
2593 {
2594 return mgl_datac_spline(this, x * (nx - 1), y * (ny - 1), z * (nz - 1));
2595 }
2596 /// Interpolate by linear function the data to given point x=[0...nx-1], y=[0...ny-1], z=[0...nz-1]
2597 dual linear(mreal x, mreal y = 0, mreal z = 0) const
2598 {
2599 return mgl_datac_linear(this, x, y, z);
2600 }
2601 /// Interpolate by line the data to given point x,\a y,\a z which normalized in range [0, 1]
2602 dual linear1(mreal x, mreal y = 0, mreal z = 0) const
2603 {
2604 return mgl_datac_linear(this, x * (nx - 1), y * (ny - 1), z * (nz - 1));
2605 }
2606 /// Interpolate by linear function the data and return its derivatives at given point x=[0...nx-1], y=[0...ny-1], z=[0...nz-1]
2607 dual linear(MglPoint* dif, mreal x, mreal y = 0, mreal z = 0) const
2608 {
2609 dual val, dx, dy, dz;
2610 val = mgl_datac_linear_ext(this, x, y, z, & dx, & dy, & dz);
2611 dif = MglPoint(dx.getReal, dy.getReal, dz.getReal);
2612 return val;
2613 }
2614 /// Interpolate by line the data and return its derivatives at given point x,\a y,\a z which normalized in range [0, 1]
2615 dual linear1(MglPoint* dif, mreal x, mreal y = 0, mreal z = 0) const
2616 {
2617 dual val, dx, dy, dz;
2618 val = mgl_datac_linear_ext(this, x, y, z, & dx, & dy, & dz);
2619 dif = MglPoint(dx.getReal, dy.getReal, dz.getReal);
2620 dif.x /= nx > 1 ? nx - 1 : 1;
2621 dif.y /= ny > 1 ? ny - 1 : 1;
2622 dif.z /= nz > 1 ? nz - 1 : 1;
2623 return val;
2624 }
2625 /// Return an approximated x-value (root) when dat(x) = val
2626 mreal solve(mreal val, bool use_spline = true, long i0 = 0) const
2627 {
2628 return mgl_data_solve_1d(this, val, use_spline, i0);
2629 }
2630 /// Return an approximated value (root) when dat(x) = val
2631 MglData solve(mreal val, char dir, bool norm = true) const
2632 {
2633 return MglData(true, mgl_data_solve(this, val, dir, 0, norm));
2634 }
2635 MglData solve(mreal val, char dir, const MglData* i0, bool norm = true) const
2636 {
2637 return MglData(true, mgl_data_solve(this, val, dir, & i0, norm));
2638 }
2639
2640 /// Copy data from other MglDataA variable
2641 MglDataA* opAssign(in MglDataA* d)
2642 {
2643 if (this != & d)
2644 set( & d);
2645 return d;
2646
2647 }
2648 auto opAssign(in MglDataC* d)
2649 {
2650 if (this != * d)
2651 this=*d;
2652 return d;
2653 }
2654 auto opAssign(dual val)
2655 {
2656 for (long i = 0; i < nx * ny * nz; i++)
2657 a[i] = val;
2658 return val;
2659 }
2660 auto opAssign(mreal val)
2661 {
2662 for (long i = 0; i < nx * ny * nz; i++)
2663 a[i] = val;
2664 return val;
2665 }
2666 static if ((!SWIG) && false)
2667 {
2668 // Direct access to the data cell
2669 /+
2670 dual & operator[](long i)
2671 {
2672 return a[i];
2673 }
2674 +/
2675
2676 }
2677
2678 debug
2679 {
2680 // get the value in given cell of the data with border checking
2681 mreal v(long i, long j = 0, long k = 0) const
2682 {
2683 return mgl_abs(mgl_datac_get_value(this, i, j, k));
2684 }
2685 /// set the value in given cell of the data
2686 void set_v(mreal val, long i, long j = 0, long k = 0)
2687 {
2688 mgl_datac_set_value(this, val, i, j, k);
2689 }
2690 }
2691 else
2692 {
2693 // get the value in given cell of the data
2694 mreal v(long i, long j = 0, long k = 0) const
2695 {
2696 return abs(a[i + nx * (j + ny * k)]);
2697 }
2698 /// set the value in given cell of the data
2699 void set_v(mreal val, long i, long j = 0, long k = 0)
2700 {
2701 a[i + nx * (j + ny * k)] = val;
2702 }
2703 }
2704
2705 mreal vthr(long i) const
2706 {
2707 return abs(a[i]);
2708 }
2709
2710 // add for speeding up !!!
2711 mreal dvx(long i, long j = 0, long k = 0) const
2712 {
2713 long i0 = i + nx * (j + ny * k);
2714 return i > 0 ? abs(i < nx - 1 ? (a[i0 + 1] - a[i0 - 1]) / mgl2 : a[i0] - a[i0 - 1]) : abs(
2715 a[i0 + 1] - a[i0]);
2716 }
2717
2718 mreal dvy(long i, long j = 0, long k = 0) const
2719 {
2720 long i0 = i + nx * (j + ny * k);
2721 return j > 0 ? abs(j < ny - 1 ? (a[i0 + nx] - a[i0 - nx]) / mgl2 : a[i0] - a[i0 - nx]) : abs(
2722 a[i0 + nx] - a[i0]);
2723 }
2724
2725 mreal dvz(long i, long j = 0, long k = 0) const
2726 {
2727 long i0 = i + nx * (j + ny * k), n = nx * ny;
2728 return k > 0 ? abs(k < nz - 1 ? (a[i0 + n] - a[i0 - n]) / mgl2 : a[i0] - a[i0 - n]) : abs(
2729 a[i0 + n] - a[i0]);
2730 }
2731 }
2732 static if(!SWIG)
2733 {
2734 dual mglLinearC(const dual * a, long nx, long ny, long nz, mreal x, mreal y, mreal z);
2735 dual mglSpline3C(const dual * a, long nx, long ny, long nz, mreal x, mreal y, mreal z, dual * dx = 0, dual * dy = 0, dual * dz = 0);
2736 dual mglSpline3Cs(const dual * a, long nx, long ny, long nz, mreal x, mreal y, mreal z);
2737 }
2738
2739 /// saves result of PDE solving (|u|^2) for "Hamiltonian" ham with initial conditions ini
2740 MglDataC mglPDEc(mglBase * gr, const char * ham, in MglDataA* ini_re,
2741 in MglDataA* ini_im, mreal dz = 0.1, mreal k0 = 100, string opt= "")
2742 {
2743 return MglDataC(true, mgl_pde_solve_c(gr, ham, & ini_re, & ini_im, dz, k0, opt.toStringz));
2744 }
2745 /// saves result of PDE solving for "Hamiltonian" ham with initial conditions ini along a curve ray (must have nx>=7 - x,y,z,px,py,pz,tau or nx=5 - x,y,px,py,tau)
2746 MglDataC mglQO2dc(const char * ham, in MglDataA* ini_re, in MglDataA* ini_im, in MglDataA* ray, mreal r = 1,
2747 mreal k0 = 100)
2748 {
2749 return MglDataC(true, mgl_qo2d_solve_c(ham, & ini_re, & ini_im, & ray, r, k0, 0, 0));
2750 }
2751
2752 MglDataC mglQO2dc(const char * ham, in MglDataA* ini_re,
2753 in MglDataA* ini_im, in MglDataA* ray, MglData* xx, MglData* yy,
2754 mreal r = 1, mreal k0 = 100)
2755 {
2756 return MglDataC(true, mgl_qo2d_solve_c(ham, & ini_re, & ini_im, & ray, r, k0,
2757 & xx, & yy));
2758 }
2759
2760 /// saves result of PDE solving for "Hamiltonian" ham with initial conditions ini along a curve ray (must have nx>=7 - x,y,z,px,py,pz,tau or nx=5 - x,y,px,py,tau)
2761 MglDataC mglQO3dc(const char * ham, in MglDataA* ini_re,
2762 in MglDataA* ini_im, in MglDataA* ray, mreal r = 1, mreal k0 = 100)
2763 {
2764 return MglDataC(true, mgl_qo3d_solve_c(ham, & ini_re, & ini_im, & ray, r, k0,
2765 0, 0, 0));
2766 }
2767
2768 MglDataC mglQO3dc(string ham, in MglDataA* ini_re, in MglDataA* ini_im, in MglDataA* ray, MglData* xx, MglData* yy,
2769 MglData* zz, mreal r = 1, mreal k0 = 100)
2770 {
2771 return MglDataC(true, mgl_qo3d_solve_c(ham.toStringz, & ini_re, & ini_im, & ray, r,
2772 k0, & xx, & yy, & zz));
2773 }
2774 //-----------------------------------------------------------------------------
2775 /// Prepare coefficients for global spline interpolation
2776 MglDataC mglGSplineCInit(in MglDataA* xdat, in MglDataA* ydat)
2777 {
2778 return MglDataC(true, mgl_gsplinec_init( & xdat, & ydat));
2779 }
2780 /// Evaluate global spline (and its derivatives d1, d2 if not NULL) using prepared coefficients \a coef
2781 dual mglGSplineC(in MglDataA* coef, mreal dx, dual * d1 = 0, dual * d2 = 0)
2782 {
2783 return mgl_gsplinec( & coef, dx, d1, d2);
2784 }
2785 auto _DN_(T)(T a)
2786 {
2787 return (cast(MglDataC * ) * (a));
2788 }
2789 auto _DC_()
2790 {
2791 return (cast(MglDataC * ) * d);
2792 }
2793
2794 static if(!SWIG)
2795 {
2796 //Wrapper class for complex expression evaluating
2797 class mglExprC
2798 {
2799 HAEX ex;
2800 this(in mglExprC* inp)
2801 {
2802 } // copying is not allowed
2803
2804 const mglExprC* opAssign(const mglExprC* t)
2805 {
2806 return t;
2807 }
2808
2809 this(string expr)
2810 {
2811 ex = mgl_create_cexpr(expr.toStringz);
2812 }
2813
2814 ~ this()
2815 {
2816 mgl_delete_cexpr(ex);
2817 }
2818
2819 // Return value of expression for given x,y,z variables
2820 dual Eval(dual x, dual y = 0, dual z = 0)
2821 {
2822 return mgl_cexpr_eval(ex, x, y, z);
2823 }
2824
2825 // Return value of expression for given x,y,z,u,v,w variables
2826 dual Eval(dual x, dual y, dual z, dual u, dual v, dual w)
2827 {
2828 dual var[26];
2829 var['x' - 'a'] = x;
2830 var['y' - 'a'] = y;
2831 var['z' - 'a'] = z;
2832 var['u' - 'a'] = u;
2833 var['v' - 'a'] = v;
2834 var['w' - 'a'] = w;
2835 return mgl_cexpr_eval_v(ex, var);
2836 }
2837 /// Return value of expression for given variables
2838 dual Eval(dual var[26])
2839 {
2840 return mgl_cexpr_eval_v(ex, var);
2841 }
2842 }
2843 }
2844
2845 /***************************************************************************
2846 * data.h is part of Math Graphic Library
2847 * Copyright (C) 2007-2014 Alexey Balakin <mathgl.abalakin@gmail.ru> *
2848 * *
2849 * This program is free software; you can redistribute it and/or modify *
2850 * it under the terms of the GNU Library General Public License as *
2851 * published by the Free Software Foundation; either version 3 of the *
2852 * License, or (at your option) any later version. *
2853 * *
2854 * This program is distributed in the hope that it will be useful, *
2855 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
2856 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
2857 * GNU General Public License for more details. *
2858 * *
2859 * You should have received a copy of the GNU Library General Public *
2860 * License along with this program; if not, write to the *
2861 * Free Software Foundation, Inc., *
2862 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
2863 ***************************************************************************/
2864 +/