1 #ifndef XT_FUNCTION_H
2 #define XT_FUNCTION_H
3 
4 #include <cmath>
5 #include <string>
6 #include <set>
7 #include <cstdlib>
8 #include <iostream>
9 
10 #include "Array.h"
11 #include "ATC_TypeDefs.h"
12 
13 namespace ATC {
14 
15   /**
16    *  @class Function
17    *  @brief Base class for functions of fields, space and time
18    */
19 
20   class Function {
21   public:
22     Function(int nargs, char** args);
~Function(void)23     virtual ~Function(void) {};
24 
25     /** name */
tag()26     const std::string & tag() { return tag_;}
27 
28     /** depdendencies */
args(void)29     virtual inline ARG_NAMES args(void) {ARG_NAMES names; return names;};
30 
31     /** (1st) derivative of function wrt to a field */
dfd(FieldName,ARGS &)32     virtual inline double dfd(FieldName /* field */, ARGS& /* args */) {return 0.0;};
dfd(FieldName,ARGS &,DENS_MAT)33     virtual inline void   dfd(FieldName /* field */, ARGS& /* args */, DENS_MAT /* vals */ ) {};
34 
35     // addl: d2fd2(field1, field2, args), linearization(), grad_args
36 
37   protected:
38     /** tag : name of function */
39     std::string tag_;
40   };
41 
42   /**
43    *  @class Function_Mgr
44    *  @brief Base class that constructs and returns UXT_Function objects based on requests
45    */
46   class Function_Mgr {
47   public:
48     /** Static instance of this class */
49     static Function_Mgr * instance();
50 
51     Function* function(char ** arg, int nargs);
52     Function* copy_function(Function* other);
53    protected:
Function_Mgr()54     Function_Mgr() {};
55     ~Function_Mgr();
56    private:
57     static Function_Mgr * myInstance_;
58     /** set to store all generated objects for later deletion */
59     std::set<Function * > pointerSet_;
60   };
61 
62 
63   /**
64    *  @class LinearFieldFunction
65    *  @brief Class for functions returning values linear a given field
66    */
67 
68   class LinearFieldFunction : public Function {
69   public:
70     LinearFieldFunction(int nargs, char** args);
~LinearFieldFunction(void)71     virtual ~LinearFieldFunction(void) {};
72 
f(double * u,double *,double)73     inline double f(double* u, double* /* x */, double /* t */) {return c1_*u[0]-c0_;}
dfd(FieldName,ARGS &)74     inline double dfd(FieldName /* field */, ARGS& /* args */) {return c1_;}
75 
76     private :
77       double c0_,c1_;
78   };
79 
80   /**
81    *  @class UXT_Function
82    *  @brief Base class for functions of fields, space and time
83    */
84 
85   class UXT_Function {
86   public:
87     UXT_Function(int nargs, double* args);
~UXT_Function(void)88     virtual ~UXT_Function(void) {};
89 
tag()90     const std::string & tag() { return tag_;}
91 
92     /** function value */
f(double *,double *,double)93     virtual inline double f(double * /* u */, double* /* x */, double /* t */) {return 0.0;};
94     /** derivative of function wrt to field */
dfdu(double *,double *,double)95     virtual inline double dfdu(double * /* u */, double* /* x */, double /* t */) {return 0.0;};
96 
97   protected:
98     /** tag : name of function */
99     std::string tag_;
100   };
101 
102   /**
103    *  @class UXT_Function_Mgr
104    *  @brief Base class that constructs and returns UXT_Function objects based on requests
105    */
106 
107 
108   class UXT_Function_Mgr {
109   public:
110     /** Static instance of this class */
111     static UXT_Function_Mgr * instance();
112 
113     UXT_Function* function(std::string & type, int nargs, double * arg);
114     UXT_Function* function(char ** arg, int nargs);
115     UXT_Function* linear_function(double c0, double c1);
116     UXT_Function* copy_UXT_function(UXT_Function* other);
117    protected:
UXT_Function_Mgr()118     UXT_Function_Mgr() {};
119     ~UXT_Function_Mgr();
120    private:
121     static UXT_Function_Mgr * myInstance_;
122     /** set to store all generated objects for later deletion */
123     std::set<UXT_Function * > pointerSet_;
124   };
125 
126 
127   /**
128    *  @class ScalarLinearFunction
129    *  @brief Class for functions returning values linear in space
130    */
131 
132   class ScalarLinearFunction : public UXT_Function {
133   public:
134     ScalarLinearFunction(int nargs, double* args);
~ScalarLinearFunction(void)135     virtual ~ScalarLinearFunction(void) {};
136 
137     //inline double f(double* u, double* x, double t) {return c1_*(u[0]-c0_);}
138 
f(double * u,double *,double)139     inline double f(double* u, double* /* x */, double /* t */) {return c1_*u[0]+c0_;}
dfdu(double *,double *,double)140     inline double dfdu(double* /* u */, double* /* x */, double /* t */) {return c1_;}
141 
142     private :
143       double c0_,c1_;
144   };
145 
146   /**
147    *  @class XT_Function
148    *  @brief Base class for functions based on space and time variables
149    */
150 
151   class XT_Function {
152   public:
153     XT_Function(int nargs, double* args);
~XT_Function(void)154     virtual ~XT_Function(void) {};
155 
tag()156     const std::string & tag() { return tag_;}
157 
158     /** function value */
f(double *,double)159     virtual inline double f(double* /* x */, double /* t */) {return 0.0;};
160     /** time derivative of function */
dfdt(double *,double)161     virtual inline double dfdt(double* /* x */, double /* t */) {return 0.0;};
162     /** 2nd time derivative of function */
ddfdt(double *,double)163     virtual inline double ddfdt(double* /* x */, double /* t */) {return 0.0;};
164     /** 3rd time derivative of function */
dddfdt(double *,double)165     virtual inline double dddfdt(double* /* x */, double /* t */) {return 0.0;};
166 
167   protected:
168     /** mask : masks x,y,z dependence, x0 : origin */
169     double mask[3], x0[3];
170     /** tag : name of function */
171     std::string tag_;
172   };
173 
174   /**
175    *  @class XT_Function_Mgr
176    *  @brief Base class that constructs and returns XT_Function objects based on requests
177    */
178 
179   class XT_Function_Mgr {
180   public:
181     /** Static instance of this class */
182     static XT_Function_Mgr * instance();
183 
184     XT_Function* function(std::string & type, int nargs, double * arg);
185     XT_Function* function(char ** arg, int nargs);
186     XT_Function* constant_function(double c);
187     XT_Function* copy_XT_function(XT_Function* other);
188    protected:
XT_Function_Mgr()189     XT_Function_Mgr() {};
190     ~XT_Function_Mgr();
191    private:
192     static XT_Function_Mgr * myInstance_;
193     /** set to store all generated objects for later deletion */
194     std::set<XT_Function * > pointerSet_;
195 
196   };
197 
198   //------------------------------------------------------------------------
199   // derived classes
200   //------------------------------------------------------------------------
201 
202   /**
203    *  @class ConstantFunction
204    *  @brief Class for functions returning constant values
205    */
206 
207   class ConstantFunction : public XT_Function {
208   public:
209     ConstantFunction(int nargs, double* args);
210     ConstantFunction(double arg);
~ConstantFunction(void)211     virtual ~ConstantFunction(void) {};
212 
f(double *,double)213     inline double f(double* /* x */, double /* t */)
214     {return C0;};
215 
216     private :
217       double C0;
218   };
219 
220   /**
221    *  @class LinearFunction
222    *  @brief Class for functions returning values linear in space
223    */
224 
225   class LinearFunction : public XT_Function {
226   public:
227     LinearFunction(int nargs, double* args);
~LinearFunction(void)228     virtual ~LinearFunction(void) {};
229 
f(double * x,double)230     double f(double* x, double /* t */)
231       {return mask[0]*(x[0]-x0[0])+mask[1]*(x[1]-x0[1])+mask[2]*(x[2]-x0[2]) + C0;};
232 
233     private :
234       double C0;
235   };
236   /**
237    *  @class PiecewiseLinearFunction
238    *  @brief Class for functions returning values piecewise linear in space
239    *  along given direction
240    */
241 
242   class PiecewiseLinearFunction : public XT_Function {
243   public:
244     PiecewiseLinearFunction(int nargs, double* args);
~PiecewiseLinearFunction(void)245     virtual ~PiecewiseLinearFunction(void) {};
246 
247     double f(double* x, double t) ;
248 
249     private :
250       Array<double> xi;
251       Array<double> fi;
252   };
253 
254   /**
255    *  @class LinearTemporalRamp
256    *  @brief Class for functions returning values linear in space and time
257    */
258 
259   class LinearTemporalRamp : public XT_Function {
260   public:
261     LinearTemporalRamp(int nargs, double* args);
~LinearTemporalRamp(void)262     ~LinearTemporalRamp(void) {};
263 
264     double f(double* x, double t);
265     double dfdt(double* x, double t);
266 
267     protected :
268       double mask_slope[3];
269       double C0_initial, C0_slope;
270 
271   };
272 
273   /**
274    *  @class QuadraticFunction
275    *  @brief Class for functions returning values quadratic in space
276    */
277 
278   class QuadraticFunction : public XT_Function {
279   public:
280     QuadraticFunction(int nargs, double* args);
~QuadraticFunction(void)281     virtual ~QuadraticFunction(void) {};
282 
f(double * x,double)283     inline double f(double* x, double /* t */)
284       {return
285        C2[0]*(x[0]-x0[0])*(x[0]-x0[0])+
286        C2[1]*(x[1]-x0[1])*(x[1]-x0[1])+
287        C2[2]*(x[2]-x0[2])*(x[2]-x0[2])+
288        2.0*C2[3]*(x[0]-x0[0])*(x[1]-x0[1]) +
289        2.0*C2[4]*(x[0]-x0[0])*(x[2]-x0[2]) +
290        2.0*C2[5]*(x[1]-x0[1])*(x[2]-x0[2]) +
291        mask[0]*(x[0]-x0[0])+mask[1]*(x[1]-x0[1])+mask[2]*(x[2]-x0[2]) + C0;};
292 
293     private :
294       double C0, C2[6]; // C2 1:xx 2:yy 3:zz 4:xy|yx 5:xz|zx 6:yz|zy
295   };
296 
297   /**
298    *  @class SineFunction
299    *  @brief Class for functions returning values sinusoidally varying in space and time
300    */
301 
302   class SineFunction : public XT_Function {
303   public:
304     SineFunction(int nargs, double* args);
~SineFunction(void)305     virtual ~SineFunction(void){};
306 
f(double * x,double t)307     inline double f(double* x, double t)
308       {return  C*sin( mask[0]*(x[0]-x0[0])
309                      +mask[1]*(x[1]-x0[1])
310                      +mask[2]*(x[2]-x0[2]) - w*t) + C0;};
311 
312     private :
313       double C, C0, w;
314   };
315 
316   /**
317    *  @class GaussianFunction
318    *  @brief Class for functions returning values according to a Gaussian distribution in space
319    */
320 
321   class GaussianFunction : public XT_Function {
322   public:
323     GaussianFunction(int nargs, double* args);
~GaussianFunction(void)324     virtual ~GaussianFunction(void){};
325 
326     // 1/(2 pi \sigma)^(n/2) exp(-1/2 x.x/\sigma^2 ) for n = dimension
f(double * x,double)327     inline double f(double* x, double /* t */)
328       {return  C*exp(-(mask[0]*(x[0]-x0[0])*(x[0]-x0[0])
329                       +mask[1]*(x[1]-x0[1])*(x[1]-x0[1])
330                       +mask[2]*(x[2]-x0[2])*(x[2]-x0[2]))/tau/tau) + C0;};
331 
332     protected:
333       double tau, C, C0;
334   };
335 
336   /**
337    *  @class GaussianTemporalRamp
338    *  @brief Class for functions returning values according to a Gaussian distribution in space and linearly in time
339    */
340 
341   class GaussianTemporalRamp : public GaussianFunction {
342   public:
343     GaussianTemporalRamp(int nargs, double* args);
~GaussianTemporalRamp(void)344     virtual ~GaussianTemporalRamp(void){};
345 
346     double f(double* x, double t);
347     double dfdt(double* x, double t);
348 
349   protected:
350     double tau_initial, tau_slope;
351     double C_initial, C_slope;
352     double C0_initial, C0_slope;
353   };
354 
355   /**
356    *  @class TemporalRamp
357    *  @brief Class for functions returning values constant in space and varying linearly in time
358    */
359 
360   class TemporalRamp : public XT_Function {
361   public:
362     TemporalRamp(int nargs, double* args);
~TemporalRamp(void)363     virtual ~TemporalRamp(void) {};
364 
f(double *,double t)365     inline double f(double* /* x */, double t)
366     {return f_initial + slope*t;};
367 
dfdt(double *,double)368     inline double dfdt(double* /* x */, double /* t */)
369     {return slope;};
370 
371     private :
372       double f_initial, slope;
373   };
374 
375   /**
376    *  @class RadialPower
377    *  @brief Class for functions returning values based on distance from a fix point raised to a specified power
378    */
379 
380   class RadialPower : public XT_Function {
381   public:
382     RadialPower(int nargs, double* args);
~RadialPower(void)383     virtual ~RadialPower(void) {};
384 
f(double * x,double)385     inline double f(double* x, double /* t */)
386     {
387       double dx = x[0]-x0[0]; double dy = x[1]-x0[1]; double dz = x[2]-x0[2];
388       double r = mask[0]*dx*dx+mask[1]*dy*dy+mask[2]*dz*dz; r = sqrt(r);
389       return C0*pow(r,n);
390     };
391 
392   private :
393     double C0, n;
394   };
395 
396   /**
397    *  @class InterpolationFunction
398    *  @brief Base class for interpolation functions
399    */
400 
401   class InterpolationFunction {
402   public:
InterpolationFunction(void)403     InterpolationFunction(void) : npts_(0) {};
~InterpolationFunction(void)404     virtual ~InterpolationFunction(void) {};
405 
406     /** populate data */
407     void initialize(int npts,std::fstream &fileId, double coef = 1.);
408 
409     /** function value */
410     double f(const double t) const;
411     /** derivative of function */
412     double dfdt(const double t) const;
413 
414   protected:
415     double coordinate(double x,
416       double & f0, double & fp0, double & f1, double & fp1, double & inv_dx) const;
417     int npts_;
418     Array<double> xs_;
419     Array<double> fs_;
420     Array<double> fps_;
421   };
422 
423 }
424 #endif
425