Jpp 21.0.0-rc.1
the software that should make you happy
Loading...
Searching...
No Matches
JMathlib.hh
Go to the documentation of this file.
1#ifndef __JMATH__JMATHLIB__
2#define __JMATH__JMATHLIB__
3
4#include <cstddef>
5#include <cmath>
6#include <array>
7#include <utility>
8#include <memory>
9
10
11/**
12 * \file
13 * Functional algebra.
14 *
15 * \author mdejong
16 */
17
18namespace JMATH {}
19namespace JPP { using namespace JMATH; }
20
21namespace JMATH {
22
23
24 /**
25 * Type definition for list of parameters.
26 *
27 * The template argument refers to the function that could be fitted to some data.\n
28 * The parameters of the function should be data members of type <tt>double</tt>.
29 */
30 template<class JF1_t, size_t N>
32
33
34 /**
35 * Auxiliary method to join parameter and list of parameters.
36 *
37 * \param parameters parameter list
38 * \param ls indices of parameter list
39 * \param parameter parameter
40 * \return parameter list
41 */
42 template<typename U, typename V, typename W, size_t ...i>
43 constexpr parameter_list<U, sizeof...(i) + 1> join(const parameter_list<V, sizeof...(i)>& parameters,
44 const std::index_sequence<i...>& ls,
45 double W::* parameter)
46 {
47 return {parameters[i]..., parameter};
48 };
49
50
51 /**
52 * Join parameter and list of parameters.
53 *
54 * \param parameters parameter list
55 * \param parameter parameter
56 * \return parameter list
57 */
58 template<typename U, typename V, size_t N, typename W>
60 double W::* parameter)
61 {
62 return join<U>(parameters, std::make_index_sequence<N>{}, parameter);
63 }
64
65
66 /**
67 * Auxiliary method to join two parameter lists.
68 *
69 * \param v first parameter list
70 * \param lv indices of first parameter list
71 * \param w second parameter list
72 * \param lw indices of second parameter list
73 * \return parameter list
74 */
75 template<typename U, typename V, typename W, size_t ...iv, size_t ...iw>
76 constexpr parameter_list<U, sizeof...(iv) + sizeof...(iw)> join(const parameter_list<V, sizeof...(iv)>& v,
77 const std::index_sequence<iv...>& lv,
78 const parameter_list<W, sizeof...(iw)>& w,
79 const std::index_sequence<iw...>& lw)
80 {
81 return {v[iv]..., w[iw]... };
82 };
83
84
85 /**
86 * Join two parameter lists.
87 *
88 * \param v first parameter list
89 * \param w second parameter list
90 * \return parameter list
91 */
92 template<typename U, typename V, size_t NV, typename W, size_t NW>
94 const parameter_list<W, NW>& w)
95 {
96 return join<U>(v, std::make_index_sequence<NV>{},
97 w, std::make_index_sequence<NW>{});
98 }
99
100
101 /**
102 * Auxiliary method to convert parameter list.
103 *
104 * \param parameters parameter list
105 * \param ls indices of parameter list
106 * \return parameter list
107 */
108 template<typename U, typename V, size_t ...i>
109 constexpr parameter_list<U, sizeof...(i)> convert(const parameter_list<V, sizeof...(i)>& parameters,
110 const std::index_sequence<i...>& ls)
111 {
112 return {parameters[i]...};
113 };
114
115
116 /**
117 * Convert parameter list.
118 *
119 * \param parameters parameter list
120 * \return parameter list
121 */
122 template<typename U, typename V, size_t N>
124 {
125 return convert<U>(parameters, std::make_index_sequence<N>{});
126 }
127
128
129 /**
130 * Get number of parameters.
131 *
132 * \return number of parameters
133 */
134 template<class JF1_t>
135 constexpr size_t getNumberOfParameters()
136 {
137 return JF1_t::parameters.size();
138 }
139
140
141 /**
142 * Set values of all parameters.
143 *
144 * \param f1 pointer to function
145 * \param values pointer to list of values
146 */
147 template<class JF1_t>
148 inline void setParameters(JF1_t* f1, const double* values)
149 {
150 if (f1 != NULL && values != NULL) {
151 for (size_t i = 0; i != getNumberOfParameters<JF1_t>(); ++i) {
152 (*f1)[i] = values[i];
153 }
154 }
155 }
156
157
158 /**
159 * Auxiliary base class for mathematical operations on parameters of function.
160 */
161 template<class JF1_t>
162 struct JCalculus
163 {
164 /**
165 * Negate function.
166 *
167 * \return this function
168 */
169 JF1_t& negate()
170 {
171 for (const auto& i : JF1_t::parameters) {
172 static_cast<JF1_t&>(*this).*i = -(static_cast<JF1_t&>(*this).*i);
173 }
174
175 return static_cast<JF1_t&>(*this);
176 }
177
178
179 /**
180 * Add function.
181 *
182 * \param f1 function
183 * \return this function
184 */
185 JF1_t& add(const JF1_t& f1)
186 {
187 for (const auto& i : JF1_t::parameters) {
188 static_cast<JF1_t&>(*this).*i += f1.*i;
189 }
190
191 return static_cast<JF1_t&>(*this);
192 }
193
194
195 /**
196 * Subtract function.
197 *
198 * \param f1 function
199 * \return this function
200 */
201 JF1_t& sub(const JF1_t& f1)
202 {
203 for (const auto& i : JF1_t::parameters) {
204 static_cast<JF1_t&>(*this).*i -= f1.*i;
205 }
206
207 return static_cast<JF1_t&>(*this);
208 }
209
210
211 /**
212 * Scale function.
213 *
214 * \param factor factor
215 * \return this function
216 */
217 JF1_t& mul(const double factor)
218 {
219 for (const auto& i : JF1_t::parameters) {
220 static_cast<JF1_t&>(*this).*i *= factor;
221 }
222
223 return static_cast<JF1_t&>(*this);
224 }
225
226
227 /**
228 * Scale function.
229 *
230 * \param factor factor
231 * \return this function
232 */
233 JF1_t& div(const double factor)
234 {
235 for (const auto& i : JF1_t::parameters) {
236 static_cast<JF1_t&>(*this).*i /= factor;
237 }
238
239 return static_cast<JF1_t&>(*this);
240 }
241
242
243 /**
244 * Add function.
245 *
246 * \param function this function
247 * \param value value
248 * \return this function
249 */
250 friend JF1_t& operator+=(JF1_t& function, const JF1_t& value)
251 {
252 return function.add(value);
253 }
254
255
256 /**
257 * Subtract function.
258 *
259 * \param function this function
260 * \param value value
261 * \return this function
262 */
263 friend JF1_t& operator-=(JF1_t& function, const JF1_t& value)
264 {
265 return function.sub(value);
266 }
267
268
269 /**
270 * Scale function.
271 *
272 * \param function this function
273 * \param factor factor
274 * \return this function
275 */
276 friend JF1_t& operator*=(JF1_t& function, const double factor)
277 {
278 return function.mul(factor);
279 }
280
281
282 /**
283 * Scale function.
284 *
285 * \param function this function
286 * \param factor factor
287 * \return this function
288 */
289 friend JF1_t& operator/=(JF1_t& function, const double factor)
290 {
291 return function.div(factor);
292 }
293 };
294
295
296 template<class JF1_t>
297 struct JNegate; //!< forward declaration for negation of function.
298
299 template<class JF1_t, class JF2_t = double>
300 struct JAdd; //!< forward declaration for addition of fuction.
301
302 template<class JF1_t, class JF2_t = double>
303 struct JSub; //!< forward declaration for subtraction of fuction.
304
305 template<class JF1_t, class JF2_t = double>
306 struct JMul; //!< forward declaration for multiplication of fuction.
307
308 template<class JF1_t, class JF2_t = double>
309 struct JDiv; //!< forward declaration for division of fuction.
310
311 template<class JF1_t>
312 struct JFn; //!< forward declaration for fixed power of function.
313
314 template<class JF1_t = void>
315 struct JPf; //!< forward declaration for pointer to function.
316
317
318
319 /**
320 * Auxiliary base class for mathematical operations on functions.
321 */
322 template<class JF1_t>
323 struct JMathlib {
324 /**
325 * Function value.
326 *
327 * \param args abscissa value(s)
328 * \return function value
329 */
330 template<class ...Args>
331 double operator()(const Args& ...args) const
332 {
333 return static_cast<const JF1_t&>(*this).getValue(args...);
334 }
335
336
337 /**
338 * Affirm operator.
339 *
340 * \param function this function
341 * \return result function
342 */
343 friend const JF1_t& operator+(const JF1_t& function)
344 {
345 return function;
346 }
347
348
349 /**
350 * Negate operator.
351 *
352 * \param function this function
353 * \return result function
354 */
355 friend JNegate<JF1_t> operator-(const JF1_t& function)
356 {
357 return JNegate<JF1_t>(function);
358 }
359
360
361 /**
362 * Addition of constant value.
363 *
364 * \param f1 function
365 * \param value value
366 * \return result function
367 */
368 friend JAdd<JF1_t> operator+(const JF1_t& f1, const double value)
369 {
370 return JAdd<JF1_t>(f1, value);
371 }
372
373
374 /**
375 * Addition of constant value.
376 *
377 * \param value value
378 * \param f1 function
379 * \return result function
380 */
381 friend JAdd<JF1_t> operator+(const double value, const JF1_t& f1)
382 {
383 return JAdd<JF1_t>(f1, value);
384 }
385
386
387 /**
388 * Subtraction of constant value.
389 *
390 * \param f1 function
391 * \param value value
392 * \return result function
393 */
394 friend JSub<JF1_t> operator-(const JF1_t& f1, const double value)
395 {
396 return JSub<JF1_t>(f1, value);
397 }
398
399
400 /**
401 * Subtraction of constant value.
402 *
403 * \param f1 function
404 * \param value value
405 * \return result function
406 */
407 friend JAdd< JNegate<JF1_t> > operator-(const double value, const JF1_t& f1)
408 {
409 return JAdd< JNegate<JF1_t> >(JNegate<JF1_t>(f1), value);
410 }
411
412
413 /**
414 * Multiplication of constant value.
415 *
416 * \param f1 function
417 * \param value value
418 * \return result function
419 */
420 friend JMul<JF1_t> operator*(const JF1_t& f1, const double value)
421 {
422 return JMul<JF1_t>(f1, value);
423 }
424
425
426 /**
427 * Multiplication of constant value.
428 *
429 * \param value value
430 * \param f1 function
431 * \return result function
432 */
433 friend JMul<JF1_t> operator*(const double value, const JF1_t& f1)
434 {
435 return JMul<JF1_t>(f1, value);
436 }
437
438
439 /**
440 * Division of constant value.
441 *
442 * \param f1 function
443 * \param value value
444 * \return result function
445 */
446 friend JDiv<JF1_t> operator/(const JF1_t& f1, const double value)
447 {
448 return JDiv<JF1_t>(f1, value);
449 }
450
451
452 /**
453 * Addition of two functions.
454 *
455 * \param f1 first function
456 * \param f2 second function
457 * \return result function
458 */
459 template<class JF2_t>
460 friend JAdd<JF1_t, JF2_t> operator+(const JF1_t& f1, const JF2_t& f2)
461 {
462 return JAdd<JF1_t, JF2_t>(f1, f2);
463 }
464
465
466 /**
467 * Subtraction of two functions.
468 *
469 * \param f1 first function
470 * \param f2 second function
471 * \return result function
472 */
473 template<class JF2_t>
474 friend JSub<JF1_t, JF2_t> operator-(const JF1_t& f1, const JF2_t& f2)
475 {
476 return JSub<JF1_t, JF2_t>(f1, f2);
477 }
478
479
480 /**
481 * Multiplication of two functions.
482 *
483 * \param f1 first function
484 * \param f2 second function
485 * \return result function
486 */
487 template<class JF2_t>
488 friend JMul<JF1_t, JF2_t> operator*(const JF1_t& f1, const JF2_t& f2)
489 {
490 return JMul<JF1_t, JF2_t>(f1, f2);
491 }
492
493
494 /**
495 * Division of two functions.
496 *
497 * \param f1 first function
498 * \param f2 second function
499 * \return result function
500 */
501 template<class JF2_t>
502 friend JDiv<JF1_t, JF2_t> operator/(const JF1_t& f1, const JF2_t& f2)
503 {
504 return JDiv<JF1_t, JF2_t>(f1, f2);
505 }
506
507
508 /**
509 * Power-of operator.
510 *
511 * \param f1 function
512 * \param N power
513 * \return result function
514 */
515 friend JFn<JF1_t> operator^(const JF1_t& f1, int N)
516 {
517 return JFn<JF1_t>(f1, N);
518 }
519
520
521 /**
522 * Address-of operator.
523 *
524 * \param f1 function
525 * \return result function
526 */
527 friend JPf<JF1_t> operator&(const JF1_t& f1)
528 {
529 return JPf<JF1_t>(std::addressof(f1));
530 }
531
532
533 /**
534 * Get value of parameter at given index.
535 *
536 * \param i index
537 * \return value
538 */
539 double operator[](const size_t i) const
540 {
541 return static_cast<const JF1_t&>(*this).*JF1_t::parameters[i];
542 }
543
544
545 /**
546 * Get value of parameter at given index.
547 *
548 * \param i index
549 * \return value
550 */
551 double& operator[](const size_t i)
552 {
553 return static_cast<JF1_t&>(*this).*JF1_t::parameters[i];
554 }
555 };
556
557
558 /**
559 * Negate of function.
560 */
561 template<class JF1_t>
562 struct JNegate :
563 public JMathlib< JNegate<JF1_t> >,
564 public JF1_t
565 {
566 using JMathlib< JNegate<JF1_t> >::operator();
567 using JMathlib< JNegate<JF1_t> >::operator[];
568
569
570 /**
571 * Default constructor.
572 */
574 {}
575
576
577 /**
578 * Constructor.
579 *
580 * \param f1 function
581 */
582 JNegate(const JF1_t& f1) :
583 JF1_t(f1)
584 {}
585
586
587 /**
588 * Function value.
589 *
590 * \param args abscissa value(s)
591 * \return function value
592 */
593 template<class ...Args>
594 double getValue(const Args& ...args) const
595 {
596 return -static_cast<const JF1_t&>(*this).getValue(args...);
597 }
598
599
600 /**
601 * Derivative value.
602 *
603 * \param x abscissa value
604 * \return derivative value
605 */
606 double getDerivative(const double x) const
607 {
608 return -static_cast<const JF1_t&>(*this).getDerivative(x);
609 }
610
611
612 /**
613 * Get gradient.
614 *
615 * \param args abscissa value(s)
616 * \return gradient
617 */
618 template<class ...Args>
619 JNegate getGradient(const Args& ...args) const
620 {
621 JNegate gradient;
622
623 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(args...);
624 static_cast<JF1_t&>(gradient).negate();
625
626 return gradient;
627 }
628 };
629
630
631 /**
632 * Addition of constant value.
633 */
634 template<class JF1_t>
635 struct JAdd<JF1_t, double> :
636 public JMathlib< JAdd<JF1_t, double> >,
637 public JF1_t
638 {
639 using JMathlib< JAdd<JF1_t, double> >::operator();
640 using JMathlib< JAdd<JF1_t, double> >::operator[];
641
642
643 /**
644 * Default constructor.
645 */
647 {}
648
649
650 /**
651 * Constructor.
652 *
653 * \param f1 function
654 * \param value value
655 */
656 JAdd(const JF1_t& f1, const double value) :
657 JF1_t(f1),
658 value(value)
659 {}
660
661
662 /**
663 * Function value.
664 *
665 * \param args abscissa value(s)
666 * \return function value
667 */
668 template<class ...Args>
669 double getValue(const Args& ...args) const
670 {
671 return static_cast<const JF1_t&>(*this).getValue(args...) + value;
672 }
673
674
675 /**
676 * Derivative value.
677 *
678 * \param x abscissa value
679 * \return derivative value
680 */
681 double getDerivative(const double x) const
682 {
683 return static_cast<const JF1_t&>(*this).getDerivative(x);
684 }
685
686
687 /**
688 * Get gradient.
689 *
690 * \param args abscissa value(s)
691 * \return gradient
692 */
693 template<class ...Args>
694 JAdd getGradient(const Args& ...args) const
695 {
696 JAdd gradient;
697
698 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(args...);
699
700 return gradient;
701 }
702
703 private:
704 double value;
705 };
706
707
708 /**
709 * Subtraction of constant value.
710 */
711 template<class JF1_t>
712 struct JSub<JF1_t, double> :
713 public JMathlib< JSub<JF1_t, double> >,
714 public JF1_t
715 {
716 using JMathlib< JSub<JF1_t, double> >::operator();
717 using JMathlib< JSub<JF1_t, double> >::operator[];
718
719
720 /**
721 * Default constructor.
722 */
724 {}
725
726
727 /**
728 * Constructor.
729 *
730 * \param f1 function
731 * \param value value
732 */
733 JSub(const JF1_t& f1, const double value) :
734 JF1_t(f1),
735 value(value)
736 {}
737
738
739 /**
740 * Function value.
741 *
742 * \param args abscissa value(s)
743 * \return function value
744 */
745 template<class ...Args>
746 double getValue(const Args& ...args) const
747 {
748 return static_cast<const JF1_t&>(*this).getValue(args...) - value;
749 }
750
751
752 /**
753 * Derivative value.
754 *
755 * \param x abscissa value
756 * \return derivative value
757 */
758 double getDerivative(const double x) const
759 {
760 return static_cast<const JF1_t&>(*this).getDerivative(x);
761 }
762
763
764 /**
765 * Get gradient.
766 *
767 * \param args abscissa value(s)
768 * \return gradient
769 */
770 template<class ...Args>
771 JSub getGradient(const Args& ...args) const
772 {
773 JSub gradient;
774
775 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(args...);
776
777 return gradient;
778 }
779
780 private:
781 double value;
782 };
783
784
785 /**
786 * Multiplication of constant value.
787 */
788 template<class JF1_t>
789 struct JMul<JF1_t, double> :
790 public JMathlib< JMul<JF1_t, double> >,
791 public JF1_t
792 {
793 using JMathlib< JMul<JF1_t, double> >::operator();
794 using JMathlib< JMul<JF1_t, double> >::operator[];
795
796
797 /**
798 * Default constructor.
799 */
801 {}
802
803
804 /**
805 * Constructor.
806 *
807 * \param f1 function
808 * \param value value
809 */
810 JMul(const JF1_t& f1, const double value) :
811 JF1_t(f1),
812 value(value)
813 {}
814
815
816 /**
817 * Function value.
818 *
819 * \param args abscissa value(s)
820 * \return function value
821 */
822 template<class ...Args>
823 double getValue(const Args& ...args) const
824 {
825 return static_cast<const JF1_t&>(*this).getValue(args...) * value;
826 }
827
828
829 /**
830 * Derivative value.
831 *
832 * \param x abscissa value
833 * \return derivative value
834 */
835 double getDerivative(const double x) const
836 {
837 return static_cast<const JF1_t&>(*this).getDerivative(x) * value;
838 }
839
840
841 /**
842 * Get gradient.
843 *
844 * \param args abscissa value(s)
845 * \return gradient
846 */
847 template<class ...Args>
848 JMul getGradient(const Args& ...args) const
849 {
850 JMul gradient;
851
852 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(args...);
853 static_cast<JF1_t&>(gradient) *= value;
854
855 return gradient;
856 }
857
858 private:
859 double value;
860 };
861
862
863 /**
864 * Division of constant value.
865 */
866 template<class JF1_t>
867 struct JDiv<JF1_t, double> :
868 public JMathlib< JDiv<JF1_t, double> >,
869 public JF1_t
870 {
871 using JMathlib< JDiv<JF1_t, double> >::operator();
872 using JMathlib< JDiv<JF1_t, double> >::operator[];
873
874
875 /**
876 * Default constructor.
877 */
879 {}
880
881
882 /**
883 * Constructor.
884 *
885 * \param f1 function
886 * \param value value
887 */
888 JDiv(const JF1_t& f1, const double value) :
889 JF1_t(f1),
890 value(value)
891 {}
892
893
894 /**
895 * Function value.
896 *
897 * \param args abscissa value(s)
898 * \return function value
899 */
900 template<class ...Args>
901 double getValue(const Args& ...args) const
902 {
903 return static_cast<const JF1_t&>(*this).getValue(args...) / value;
904 }
905
906
907 /**
908 * Derivative value.
909 *
910 * \param x abscissa value
911 * \return derivative value
912 */
913 double getDerivative(const double x) const
914 {
915 return static_cast<const JF1_t&>(*this).getDerivative(x) / value;
916 }
917
918
919 /**
920 * Get gradient.
921 *
922 * \param args abscissa value(s)
923 * \return gradient
924 */
925 template<class ...Args>
926 JDiv getGradient(const Args& ...args) const
927 {
928 JDiv gradient;
929
930 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(args...);
931 static_cast<JF1_t&>(gradient) /= value;
932
933 return gradient;
934 }
935
936 private:
937 double value;
938 };
939
940
941 /**
942 * Auxiliary data structure for pair of functions.
943 */
944 template<class JF1_t, class JF2_t,
945 bool v1 = JF1_t::parameters.size() != 0 || std::is_base_of<JPf<>, JF1_t>::value, // false -> virtual base class
946 bool v2 = JF2_t::parameters.size() != 0 || std::is_base_of<JPf<>, JF2_t>::value> // false -> virtual base class
947 struct JPair :
948 public JF1_t,
949 public JF2_t
950 {
951 /**
952 * Default constructor.
953 */
955 {}
956
957
958 /**
959 * Constructor.
960 *
961 * \param f1 first function
962 * \param f2 second function
963 */
964 JPair(const JF1_t& f1, const JF2_t& f2) :
965 JF1_t(f1),
966 JF2_t(f2)
967 {}
968
969 static constexpr parameter_list<JPair, JF1_t::parameters.size() + JF2_t::parameters.size()> parameters = join<JPair>(JF1_t::parameters, JF2_t::parameters);
970 };
971
972
973 /**
974 * Template specialisation for pair of functions.
975 */
976 template<class JF1_t, class JF2_t>
977 struct JPair<JF1_t, JF2_t, true, false> :
978 public virtual JF2_t,
979 public JF1_t
980 {
981 /**
982 * Default constructor.
983 */
985 {}
986
987
988 /**
989 * Constructor.
990 *
991 * \param f1 first function
992 * \param f2 second function
993 */
994 JPair(const JF1_t& f1, const JF2_t& f2) :
995 JF1_t(f1)
996 {}
997
998 static constexpr parameter_list<JPair, JF1_t::parameters.size()> parameters = convert<JPair>(JF1_t::parameters);
999 };
1000
1001
1002 /**
1003 * Template specialisation for pair of functions.
1004 */
1005 template<class JF1_t, class JF2_t>
1006 struct JPair<JF1_t, JF2_t, false, true> :
1007 public virtual JF1_t,
1008 public JF2_t
1009 {
1010 /**
1011 * Default constructor.
1012 */
1014 {}
1015
1016
1017 /**
1018 * Constructor.
1019 *
1020 * \param f1 first function
1021 * \param f2 second function
1022 */
1023 JPair(const JF1_t& f1, const JF2_t& f2) :
1024 JF2_t(f2)
1025 {}
1026
1027 static constexpr parameter_list<JPair, JF2_t::parameters.size()> parameters = convert<JPair>(JF2_t::parameters);
1028 };
1029
1030
1031 /**
1032 * Template specialisation for pair of functions.
1033 */
1034 template<class JF1_t, class JF2_t>
1035 struct JPair<JF1_t, JF2_t, false, false> :
1036 public virtual JF1_t,
1037 public virtual JF2_t
1038 {
1039 /**
1040 * Default constructor.
1041 */
1043 {}
1044
1045
1046 /**
1047 * Constructor.
1048 *
1049 * \param f1 first function
1050 * \param f2 second function
1051 */
1052 JPair(const JF1_t& f1, const JF2_t& f2)
1053 {}
1054
1056 };
1057
1058
1059 /**
1060 * Auxiliary data structure for pair of functions.
1061 */
1062 template<class JF1_t, class JF2_t>
1063 struct JPair_t :
1064 public JPair<JF1_t, JF2_t>,
1065 public JCalculus< JPair_t<JF1_t, JF2_t> >
1066 {
1072
1073
1074 /**
1075 * Default constructor.
1076 */
1078 {}
1079
1080
1081 /**
1082 * Constructor.
1083 *
1084 * \param f1 first function
1085 * \param f2 second function
1086 */
1087 JPair_t(const JF1_t& f1, const JF2_t& f2) :
1088 JPair<JF1_t, JF2_t>(f1, f2)
1089 {}
1090 };
1091
1092
1093 /**
1094 * Addition of two functions.
1095 */
1096 template<class JF1_t, class JF2_t>
1097 struct JAdd :
1098 public JMathlib< JAdd<JF1_t, JF2_t> >,
1099 public JPair_t<JF1_t, JF2_t>
1100 {
1101 using JMathlib< JAdd<JF1_t, JF2_t> >::operator();
1102 using JMathlib< JAdd<JF1_t, JF2_t> >::operator[];
1103
1104
1105 /**
1106 * Default constructor.
1107 */
1109 {}
1110
1111
1112 /**
1113 * Constructor.
1114 *
1115 * \param f1 first function
1116 * \param f2 second function
1117 */
1118 JAdd(const JF1_t& f1, const JF2_t& f2) :
1119 JPair_t<JF1_t, JF2_t>(f1, f2)
1120 {}
1121
1122
1123 /**
1124 * Function value.
1125 *
1126 * \param args abscissa value(s)
1127 * \return function value
1128 */
1129 template<class ...Args>
1130 double getValue(const Args& ...args) const
1131 {
1132 return (static_cast<const JF1_t&>(*this).getValue(args...) +
1133 static_cast<const JF2_t&>(*this).getValue(args...));
1134 }
1135
1136
1137 /**
1138 * Derivative value.
1139 *
1140 * \param x abscissa value
1141 * \return derivative value
1142 */
1143 double getDerivative(const double x) const
1144 {
1145 return (static_cast<const JF1_t&>(*this).getDerivative(x) +
1146 static_cast<const JF2_t&>(*this).getDerivative(x));
1147 }
1148
1149
1150 /**
1151 * Get gradient.
1152 *
1153 * \param args abscissa value(s)
1154 * \return gradient
1155 */
1156 template<class ...Args>
1157 JAdd getGradient(const Args& ...args) const
1158 {
1159 JAdd gradient;
1160
1161 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(args...);
1162 static_cast<JF2_t&>(gradient) = static_cast<const JF2_t&>(*this).getGradient(args...);
1163
1164 return gradient;
1165 }
1166 };
1167
1168
1169 /**
1170 * Subtraction of two functions.
1171 */
1172 template<class JF1_t, class JF2_t>
1173 struct JSub :
1174 public JMathlib< JSub<JF1_t, JF2_t> >,
1175 public JPair_t<JF1_t, JF2_t>
1176 {
1177 using JMathlib< JSub<JF1_t, JF2_t> >::operator();
1178 using JMathlib< JSub<JF1_t, JF2_t> >::operator[];
1179
1180
1181 /**
1182 * Default constructor.
1183 */
1185 {}
1186
1187
1188 /**
1189 * Constructor.
1190 *
1191 * \param f1 first function
1192 * \param f2 second function
1193 */
1194 JSub(const JF1_t& f1, const JF2_t& f2) :
1195 JPair_t<JF1_t, JF2_t>(f1, f2)
1196 {}
1197
1198
1199 /**
1200 * Function value.
1201 *
1202 * \param args abscissa value(s)
1203 * \return function value
1204 */
1205 template<class ...Args>
1206 double getValue(const Args& ...args) const
1207 {
1208 return (static_cast<const JF1_t&>(*this).getValue(args...) -
1209 static_cast<const JF2_t&>(*this).getValue(args...));
1210 }
1211
1212
1213 /**
1214 * Derivative value.
1215 *
1216 * \param x abscissa value
1217 * \return derivative value
1218 */
1219 double getDerivative(const double x) const
1220 {
1221 return (static_cast<const JF1_t&>(*this).getDerivative(x) -
1222 static_cast<const JF2_t&>(*this).getDerivative(x));
1223 }
1224
1225
1226 /**
1227 * Get gradient.
1228 *
1229 * \param args abscissa value(s)
1230 * \return gradient
1231 */
1232 template<class ...Args>
1233 JSub getGradient(const Args& ...args) const
1234 {
1235 JSub gradient;
1236
1237 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(args...);
1238 static_cast<JF2_t&>(gradient) = static_cast<const JF2_t&>(*this).getGradient(args...);
1239 static_cast<JF2_t&>(gradient).negate();
1240
1241 return gradient;
1242 }
1243 };
1244
1245
1246 /**
1247 * Multiplication of two functions.
1248 */
1249 template<class JF1_t, class JF2_t>
1250 struct JMul :
1251 public JMathlib< JMul<JF1_t, JF2_t> >,
1252 public JPair_t<JF1_t, JF2_t>
1253 {
1254 using JMathlib< JMul<JF1_t, JF2_t> >::operator();
1255 using JMathlib< JMul<JF1_t, JF2_t> >::operator[];
1256
1257
1258 /**
1259 * Default constructor.
1260 */
1262 {}
1263
1264
1265 /**
1266 * Constructor.
1267 *
1268 * \param f1 first function
1269 * \param f2 second function
1270 */
1271 JMul(const JF1_t& f1, const JF2_t& f2) :
1272 JPair_t<JF1_t, JF2_t>(f1, f2)
1273 {}
1274
1275
1276 /**
1277 * Function value.
1278 *
1279 * \param args abscissa value(s)
1280 * \return function value
1281 */
1282 template<class ...Args>
1283 double getValue(const Args& ...args) const
1284 {
1285 return (static_cast<const JF1_t&>(*this).getValue(args...) *
1286 static_cast<const JF2_t&>(*this).getValue(args...));
1287 }
1288
1289
1290 /**
1291 * Derivative value.
1292 *
1293 * \param x abscissa value
1294 * \return derivative value
1295 */
1296 double getDerivative(const double x) const
1297 {
1298 return (static_cast<const JF1_t&>(*this).getDerivative(x) * static_cast<const JF2_t&>(*this).getValue(x) +
1299 static_cast<const JF1_t&>(*this).getValue(x) * static_cast<const JF2_t&>(*this).getDerivative(x));
1300 }
1301
1302
1303 /**
1304 * Get gradient.
1305 *
1306 * \param args abscissa value(s)
1307 * \return gradient
1308 */
1309 template<class ...Args>
1310 JMul getGradient(const Args& ...args) const
1311 {
1312 JMul gradient;
1313
1314 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(args...);
1315 static_cast<JF1_t&>(gradient) *= static_cast<const JF2_t&>(*this).getValue(args...);
1316 static_cast<JF2_t&>(gradient) = static_cast<const JF2_t&>(*this).getGradient(args...);
1317 static_cast<JF2_t&>(gradient) *= static_cast<const JF1_t&>(*this).getValue(args...);
1318
1319 return gradient;
1320 }
1321 };
1322
1323
1324 /**
1325 * Division of two functions.
1326 */
1327 template<class JF1_t, class JF2_t>
1328 struct JDiv :
1329 public JMathlib< JDiv<JF1_t, JF2_t> >,
1330 public JPair_t<JF1_t, JF2_t>
1331 {
1332 using JMathlib< JDiv<JF1_t, JF2_t> >::operator();
1333 using JMathlib< JDiv<JF1_t, JF2_t> >::operator[];
1334
1335
1336 /**
1337 * Default constructor.
1338 */
1340 {}
1341
1342
1343 /**
1344 * Constructor.
1345 *
1346 * \param f1 first function
1347 * \param f2 second function
1348 */
1349 JDiv(const JF1_t& f1, const JF2_t& f2) :
1350 JPair_t<JF1_t, JF2_t>(f1, f2)
1351 {}
1352
1353
1354 /**
1355 * Function value.
1356 *
1357 * \param args abscissa value(s)
1358 * \return function value
1359 */
1360 template<class ...Args>
1361 double getValue(const Args& ...args) const
1362 {
1363 return (static_cast<const JF1_t&>(*this).getValue(args...) /
1364 static_cast<const JF2_t&>(*this).getValue(args...));
1365 }
1366
1367
1368 /**
1369 * Derivative value.
1370 *
1371 * \param x abscissa value
1372 * \return derivative value
1373 */
1374 double getDerivative(const double x) const
1375 {
1376 const double v = static_cast<const JF1_t&>(*this).getValue(x);
1377 const double w = static_cast<const JF2_t&>(*this).getValue(x);
1378
1379 return (static_cast<const JF1_t&>(*this).getDerivative(x) * w -
1380 v * static_cast<const JF2_t&>(*this).getDerivative(x)) / (w*w);
1381 }
1382
1383
1384 /**
1385 * Get gradient.
1386 *
1387 * \param args abscissa value(s)
1388 * \return gradient
1389 */
1390 template<class ...Args>
1391 JDiv getGradient(const Args& ...args) const
1392 {
1393 JDiv gradient;
1394
1395 const double v = static_cast<const JF1_t&>(*this).getValue(args...);
1396 const double w = static_cast<const JF2_t&>(*this).getValue(args...);
1397
1398 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(args...);
1399 static_cast<JF1_t&>(gradient) *= 1.0/w;
1400 static_cast<JF2_t&>(gradient) = static_cast<const JF2_t&>(*this).getGradient(args...);
1401 static_cast<JF2_t&>(gradient) *= -v/(w*w);
1402
1403 return gradient;
1404 }
1405 };
1406
1407
1408 /**
1409 * Fixed power of function.
1410 */
1411 template<class JF1_t>
1412 struct JFn :
1413 public JMathlib < JFn<JF1_t> >,
1414 public JF1_t
1415 {
1416 using JMathlib< JFn<JF1_t> >::operator();
1417 using JMathlib< JFn<JF1_t> >::operator[];
1418
1419
1420 /**
1421 * Default constructor.
1422 */
1424 JF1_t(),
1425 N(1)
1426 {}
1427
1428
1429 /**
1430 * Constructor.
1431 *
1432 * \param f1 first function
1433 * \param N power
1434 */
1435 JFn(const JF1_t& f1, const int N) :
1436 JF1_t(f1),
1437 N(N)
1438 {}
1439
1440
1441 /**
1442 * Function value.
1443 *
1444 * \param args abscissa value(s)
1445 * \return function value
1446 */
1447 template<class ...Args>
1448 double getValue(const Args& ...args) const
1449 {
1450 const double u = static_cast<const JF1_t&>(*this).getValue(args...);
1451
1452 return pow(u, N);
1453 }
1454
1455
1456 /**
1457 * Derivative value.
1458 *
1459 * \param x abscissa value
1460 * \return derivative value
1461 */
1462 double getDerivative(const double x) const
1463 {
1464 const double u = static_cast<const JF1_t&>(*this).getValue(x);
1465 const double v = static_cast<const JF1_t&>(*this).getDerivative(x);
1466
1467 return N * pow(u, N - 1) * v;
1468 }
1469
1470
1471 /**
1472 * Get gradient.
1473 *
1474 * \param args abscissa value(s)
1475 * \return gradient
1476 */
1477 template<class ...Args>
1478 JFn getGradient(const Args& ...args) const
1479 {
1480 JFn gradient;
1481
1482 const double u = static_cast<const JF1_t&>(*this).getValue(args...);
1483 const double w = N * pow(u, N - 1);
1484
1485 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(args...);
1486 static_cast<JF1_t&>(gradient) *= w;
1487
1488 return gradient;
1489 }
1490
1491 private:
1492 int N;
1493 };
1494
1495
1496 /**
1497 * x.
1498 */
1499 struct JX :
1500 public JMathlib < JX >,
1501 public JCalculus< JX >
1502 {
1503 /**
1504 * Default constructor.
1505 */
1507 {}
1508
1509
1510 /**
1511 * Function value.
1512 *
1513 * \param x abscissa value
1514 * \return function value
1515 */
1516 double getValue(const double x) const
1517 {
1518 return x;
1519 }
1520
1521
1522 /**
1523 * Derivative value.
1524 *
1525 * \param x abscissa value
1526 * \return derivative value
1527 */
1528 double getDerivative(const double x) const
1529 {
1530 return 1.0;
1531 }
1532
1533
1534 /**
1535 * Get gradient.
1536 *
1537 * \param x abscissa value
1538 * \return gradient
1539 */
1540 JX getGradient(const double x) const
1541 {
1542 JX gradient;
1543
1544 return gradient;
1545 }
1546
1548 };
1549
1550
1551 static const JX X; //! Function object for x;
1552
1553
1554 /**
1555 * Fixed power of x.
1556 */
1557 template<int N>
1558 struct JXn :
1559 public JMathlib < JXn<N> >,
1560 public JCalculus< JXn<N> >
1561 {
1562 /**
1563 * Default constructor.
1564 */
1566 {}
1567
1568
1569 /**
1570 * Function value.
1571 *
1572 * \param x abscissa value
1573 * \return function value
1574 */
1575 double getValue(const double x) const
1576 {
1577 return pow(x, N);
1578 }
1579
1580
1581 /**
1582 * Derivative value.
1583 *
1584 * \param x abscissa value
1585 * \return derivative value
1586 */
1587 double getDerivative(const double x) const
1588 {
1589 return N * pow(x, N - 1);
1590 }
1591
1592
1593 /**
1594 * Get gradient.
1595 *
1596 * \param x abscissa value
1597 * \return gradient
1598 */
1599 JXn getGradient(const double x) const
1600 {
1601 JXn gradient;
1602
1603 return gradient;
1604 }
1605
1607 };
1608
1609
1610 template<>
1611 struct JXn<0>; //! Invalidate x^0.
1612 static const JXn<2> X2; //! Function object for x^2;
1613 static const JXn<3> X3; //! Function object for x^3;
1614 static const JXn<4> X4; //! Function object for x^4;
1615 static const JXn<5> X5; //! Function object for x^5;
1616
1617
1618 /**
1619 * Auxiliary base class for pointer to function.
1620 */
1621 template<>
1622 struct JPf<void>
1623 {};
1624
1625 /**
1626 * Pointer to function.
1627 */
1628 template<class JF1_t>
1629 struct JPf :
1630 public JPf<>,
1631 public JMathlib < JPf<JF1_t> >,
1632 public JCalculus< JPf<JF1_t> >
1633 {
1634 using JMathlib< JPf<JF1_t> >::operator();
1635 using JMathlib< JPf<JF1_t> >::operator[];
1636
1637
1638 /**
1639 * Default constructor.
1640 */
1642 f1(NULL)
1643 {}
1644
1645
1646 /**
1647 * Constructor.
1648 *
1649 * \param f1 pointer to function
1650 */
1651 JPf(const JF1_t* f1) :
1652 f1(f1)
1653 {}
1654
1655
1656 /**
1657 * Function value.
1658 *
1659 * \param args abscissa value(s)
1660 * \return function value
1661 */
1662 template<class ...Args>
1663 double getValue(const Args& ...args) const
1664 {
1665 return f1->getValue(args...);
1666 }
1667
1668
1669 /**
1670 * Derivative value.
1671 *
1672 * \param x abscissa value
1673 * \return derivative value
1674 */
1675 double getDerivative(const double x) const
1676 {
1677 return f1->getDerivative(x);
1678 }
1679
1680
1681 /**
1682 * Get gradient.
1683 *
1684 * \param args abscissa value(s)
1685 * \return gradient
1686 */
1687 template<class ...Args>
1688 JPf getGradient(const Args& ...args) const
1689 {
1690 JPf gradient;
1691
1692 return gradient;
1693 }
1694
1696
1697 private:
1698 const JF1_t* f1;
1699 };
1700
1701
1702 /**
1703 * Recursive template class for polynomial function.
1704 */
1705 template<int ID_t, size_t N>
1706 struct JPolynome :
1707 public JMathlib < JPolynome<ID_t, N> >,
1708 public JCalculus< JPolynome<ID_t, N> >,
1709 public JPolynome<ID_t, N - 1>
1710 {
1711 static const int ID = ID_t;
1712
1713 static const size_t NUMBER_OF_DEGREES = N;
1714
1720 using JMathlib < JPolynome<ID_t, N> >::operator();
1721 using JMathlib < JPolynome<ID_t, N> >::operator[];
1722
1723
1724 /**
1725 * Default constructor.
1726 */
1728 a(0.0)
1729 {}
1730
1731
1732 /**
1733 * Constructor.
1734 *
1735 * \param args list of values
1736 */
1737 template<class ...Args>
1738 JPolynome(const Args& ...args) :
1739 JPolynome()
1740 {
1741 set(args...);
1742 }
1743
1744
1745 /**
1746 * Constructor.
1747 *
1748 * \param args list of values
1749 */
1751 JPolynome()
1752 {
1753 for (size_t i = 0; i <= N; ++i) {
1754 (*this)[i] = std::data(args)[i];
1755 }
1756 }
1757
1758
1759 /**
1760 * Function value.
1761 *
1762 * \param x abscissa value
1763 * \return function value
1764 */
1765 double getValue(const double x) const
1766 {
1767 return a * pow(x,N) + static_cast<const JPolynome<ID_t, N - 1>&>(*this).getValue(x);
1768 }
1769
1770
1771 /**
1772 * Derivative value.
1773 *
1774 * \param x abscissa value
1775 * \return derivative value
1776 */
1777 double getDerivative(const double x) const
1778 {
1779 return N * a * pow(x,N-1) + static_cast<const JPolynome<ID_t, N - 1>&>(*this).getDerivative(x);
1780 }
1781
1782
1783 /**
1784 * Get gradient.
1785 *
1786 * \param x abscissa value
1787 * \return gradient
1788 */
1789 JPolynome getGradient(const double x) const
1790 {
1791 JPolynome gradient;
1792
1793 gradient.a = pow(x,N);
1794
1795 static_cast<JPolynome<ID_t, N - 1>&>(gradient) = static_cast<const JPolynome<ID_t, N - 1>&>(*this).getGradient(x);
1796
1797 return gradient;
1798 }
1799
1800 double a; //!< a[N]
1801
1803
1804 protected:
1805 /**
1806 * Recursive method for setting values.
1807 *
1808 * \param x first value
1809 * \param args remaining values
1810 */
1811 template<class ...Args>
1812 void set(const double x, const Args& ...args)
1813 {
1814 a = x;
1815
1817 }
1818 };
1819
1820
1821 /**
1822 * Termination class for polynomial function.
1823 * This function consititutes a constant term and is thereby multi-dimensional by nature.
1824 */
1825 template<int ID_t>
1826 struct JPolynome<ID_t, 0> :
1827 public JMathlib < JPolynome<ID_t, 0> >,
1828 public JCalculus< JPolynome<ID_t, 0> >
1829 {
1830 static const int ID = ID_t;
1831
1832 static const size_t NUMBER_OF_DEGREES = 0;
1833
1834
1835 /**
1836 * Default constructor.
1837 */
1839 a(0.0)
1840 {}
1841
1842
1843 /**
1844 * Constructor.
1845 *
1846 * \param a value
1847 */
1848 JPolynome(const double a) :
1849 a(a)
1850 {}
1851
1852
1853 /**
1854 * Constructor.
1855 *
1856 * \param args list of values
1857 */
1859 JPolynome()
1860 {
1861 a = std::data(args)[0];
1862 }
1863
1864
1865 /**
1866 * Function value.
1867 *
1868 * \return function value
1869 */
1870 double getValue(...) const
1871 {
1872 return a;
1873 }
1874
1875
1876 /**
1877 * Derivative value.
1878 *
1879 * \return derivative value
1880 */
1881 double getDerivative(...) const
1882 {
1883 return 0.0;
1884 }
1885
1886
1887 /**
1888 * Get gradient.
1889 *
1890 * \return gradient
1891 */
1893 {
1894 JPolynome gradient;
1895
1896 gradient.a = 1.0;
1897
1898 return gradient;
1899 }
1900
1901 double a; //!< a[0]
1902
1904
1905 protected:
1906 /**
1907 * Recursive method for setting values.
1908 *
1909 * \param x value
1910 */
1911 void set(const double x)
1912 {
1913 a = x;
1914 }
1915 };
1916
1917
1918 template<int ID_t>
1919 using JP0 = JPolynome<ID_t, 0>; //!< shorthand for 0th degree polynome
1920
1921 template<int ID_t>
1922 using P0 = JP0<ID_t>; //!< shorthand for constant term
1923
1924 template<int ID_t>
1925 using JP1 = JPolynome<ID_t, 1>; //!< shorthand for 1st degree polynome
1926
1927 template<int ID_t>
1928 using JP2 = JPolynome<ID_t, 2>; //!< shorthand for 2nd degree polynome
1929
1930 template<int ID_t>
1931 using JP3 = JPolynome<ID_t, 3>; //!< shorthand for 3rd degree polynome
1932
1933
1934 /**
1935 * Gauss function.
1936 */
1937 template<int ID_t, bool normalised = false>
1938 struct JGauss :
1939 public JMathlib < JGauss<ID_t> >,
1940 public JCalculus< JGauss<ID_t> >
1941 {
1942 static const int ID = ID_t;
1943
1944
1945 /**
1946 * Default constructor.
1947 */
1949 center(0.0),
1950 sigma (0.0)
1951 {}
1952
1953
1954 /**
1955 * Constructor.
1956 *
1957 * \param center center
1958 * \param sigma sigma
1959 */
1960 JGauss(const double center,
1961 const double sigma) :
1962 center(center),
1963 sigma (sigma)
1964 {}
1965
1966
1967 /**
1968 * Function value.
1969 *
1970 * \param x abscissa value
1971 * \return function value
1972 */
1973 double getValue(const double x) const
1974 {
1975 const double u = (x - center) / sigma;
1976
1977 return get(u);
1978 }
1979
1980
1981 /**
1982 * Derivative value.
1983 *
1984 * \param x abscissa value
1985 * \return derivative value
1986 */
1987 double getDerivative(const double x) const
1988 {
1989 const double w = 1.0 / sigma;
1990 const double u = (x - center) / sigma;
1991
1992 return get(u) * -u * w;
1993 }
1994
1995
1996 /**
1997 * Get gradient.
1998 *
1999 * \param x abscissa value
2000 * \return gradient
2001 */
2002 JGauss getGradient(const double x) const
2003 {
2005
2006 const double w = 1.0 / sigma;
2007 const double u = (x - center) * w;
2008 const double f0 = get(u);
2009
2010 gradient.center = f0 * u * w; // d(f)/d(center)
2011 gradient.sigma = f0 * u * u * w; // d(f)/d(sigma)
2012
2013 return gradient;
2014 }
2015
2016 double center; //!< center
2017 double sigma; //!< sigma
2018
2020
2021 private:
2022 /**
2023 * Get ordinate value.
2024 *
2025 * \param u abscissa value
2026 * \return ordinate value
2027 */
2028 inline double get(const double u) const
2029 {
2030 return exp(-0.5*u*u);
2031 }
2032 };
2033
2034
2035 /**
2036 * Gauss function.
2037 */
2038 template<int ID_t>
2039 struct JGauss<ID_t, true> :
2040 public JMathlib < JGauss<ID_t, true> >,
2041 public JCalculus< JGauss<ID_t, true> >
2042 {
2043 static const int ID = ID_t;
2044
2045
2046 /**
2047 * Default constructor.
2048 */
2050 center(0.0),
2051 sigma (0.0)
2052 {}
2053
2054
2055 /**
2056 * Constructor.
2057 *
2058 * \param center center
2059 * \param sigma sigma
2060 */
2061 JGauss(const double center,
2062 const double sigma) :
2063 center(center),
2064 sigma (sigma)
2065 {}
2066
2067
2068 /**
2069 * Function value.
2070 *
2071 * \param x abscissa value
2072 * \return function value
2073 */
2074 double getValue(const double x) const
2075 {
2076 const double u = (x - center) / sigma;
2077
2078 return get(u);
2079 }
2080
2081
2082 /**
2083 * Derivative value.
2084 *
2085 * \param x abscissa value
2086 * \return derivative value
2087 */
2088 double getDerivative(const double x) const
2089 {
2090 const double w = 1.0 / sigma;
2091 const double u = (x - center) / sigma;
2092
2093 return get(u) * -u * w;
2094 }
2095
2096
2097 /**
2098 * Get gradient.
2099 *
2100 * \param x abscissa value
2101 * \return gradient
2102 */
2103 JGauss getGradient(const double x) const
2104 {
2106
2107 const double w = 1.0 / sigma;
2108 const double u = (x - center) * w;
2109 const double f0 = get(u);
2110
2111 gradient.center = f0 * (u) * w; // d(f)/d(center)
2112 gradient.sigma = f0 * (u + 1.0) * (u - 1.0) * w; // d(f)/d(sigma)
2113
2114 return gradient;
2115 }
2116
2117 double center; //!< center
2118 double sigma; //!< sigma
2119
2121
2122 private:
2123 /**
2124 * Get ordinate value.
2125 *
2126 * \param u abscissa value
2127 * \return ordinate value
2128 */
2129 inline double get(const double u) const
2130 {
2131 static const double W = 1.0 / sqrt(2.0 * acos(-1.0));
2132
2133 return exp(-0.5*u*u) * W / sigma;
2134 }
2135 };
2136
2137
2138 /**
2139 * Power of function.
2140 */
2141 template<int ID_t, class JF1_t = JX>
2142 struct JPow :
2143 public JMathlib < JPow<ID_t, JF1_t> >,
2144 public JF1_t
2145 {
2146 static const int ID = ID_t;
2147
2148 using JMathlib< JPow<ID_t, JF1_t> >::operator();
2149 using JMathlib< JPow<ID_t, JF1_t> >::operator[];
2150
2151
2152 /**
2153 * Default constructor.
2154 */
2156 JF1_t(),
2157 alpha(0.0)
2158 {}
2159
2160
2161 /**
2162 * Constructor.
2163 *
2164 * \param alpha value
2165 */
2166 JPow(const double alpha) :
2167 JF1_t(),
2168 alpha(alpha)
2169 {}
2170
2171
2172 /**
2173 * Constructor.
2174 *
2175 * \param f1 function
2176 * \param alpha value
2177 */
2178 JPow(const JF1_t& f1, const double alpha) :
2179 JF1_t(f1),
2180 alpha(alpha)
2181 {}
2182
2183
2184 /**
2185 * Function value.
2186 *
2187 * \param x abscissa value
2188 * \return function value
2189 */
2190 double getValue(const double x) const
2191 {
2192 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2193
2194 return pow(u, alpha);
2195 }
2196
2197
2198 /**
2199 * Derivative value.
2200 *
2201 * \param x abscissa value
2202 * \return derivative value
2203 */
2204 double getDerivative(const double x) const
2205 {
2206 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2207 const double v = static_cast<const JF1_t&>(*this).getDerivative(x);
2208
2209 return alpha * pow(u, alpha - 1) * v;
2210 }
2211
2212
2213 /**
2214 * Get gradient.
2215 *
2216 * \param x abscissa value
2217 * \return gradient
2218 */
2219 JPow getGradient(const double x) const
2220 {
2221 JPow gradient;
2222
2223 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2224 const double w = pow(u, alpha);
2225
2226 gradient.alpha = w * log(u);
2227
2228 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(x);
2229 static_cast<JF1_t&>(gradient) *= alpha * w / u;
2230
2231 return gradient;
2232 }
2233
2234 double alpha; //!< f(x)^alpha
2235
2237 };
2238
2239
2240 /**
2241 * Power of function.
2242 *
2243 * \param f1 function
2244 * \param alpha alpha
2245 * \return result
2246 */
2247 template<class JF1_t>
2248 JPow<JF1_t::ID, JF1_t> Pow(const JF1_t& f1, const double alpha)
2249 {
2250 return JPow<JF1_t::ID, JF1_t>(f1, alpha);
2251 }
2252
2253
2254 /**
2255 * Square root of function.
2256 */
2257 template<class JF1_t = JX>
2258 struct JSqrt :
2259 public JMathlib < JSqrt<JF1_t> >,
2260 public JF1_t
2261 {
2262 using JMathlib< JSqrt<JF1_t> >::operator();
2263 using JMathlib< JSqrt<JF1_t> >::operator[];
2264
2265
2266 /**
2267 * Default constructor.
2268 */
2270 JF1_t()
2271 {}
2272
2273
2274 /**
2275 * Constructor.
2276 *
2277 * \param f1 function
2278 */
2279 JSqrt(const JF1_t& f1) :
2280 JF1_t(f1)
2281 {}
2282
2283
2284 /**
2285 * Function value.
2286 *
2287 * \param x abscissa value
2288 * \return function value
2289 */
2290 double getValue(const double x) const
2291 {
2292 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2293
2294 return sqrt(u);
2295 }
2296
2297
2298 /**
2299 * Derivative value.
2300 *
2301 * \param x abscissa value
2302 * \return derivative value
2303 */
2304 double getDerivative(const double x) const
2305 {
2306 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2307 const double v = static_cast<const JF1_t&>(*this).getDerivative(x);
2308
2309 return 0.5 * v / sqrt(u);
2310 }
2311
2312
2313 /**
2314 * Get gradient.
2315 *
2316 * \param x abscissa value
2317 * \return gradient
2318 */
2319 JSqrt getGradient(const double x) const
2320 {
2321 JSqrt gradient;
2322
2323 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2324
2325 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(x);
2326 static_cast<JF1_t&>(gradient) *= 0.5 / sqrt(u);
2327
2328 return gradient;
2329 }
2330 };
2331
2332
2333 /**
2334 * Square root of function.
2335 *
2336 * \param f1 function
2337 * \return result
2338 */
2339 template<class JF1_t>
2340 JSqrt<JF1_t> Sqrt(const JF1_t& f1)
2341 {
2342 return JSqrt<JF1_t>(f1);
2343 }
2344
2345
2346 /**
2347 * Sine of function.
2348 */
2349 template<class JF1_t = JX>
2350 struct JSin :
2351 public JMathlib < JSin<JF1_t> >,
2352 public JF1_t
2353 {
2354 using JMathlib< JSin<JF1_t> >::operator();
2355 using JMathlib< JSin<JF1_t> >::operator[];
2356
2357
2358 /**
2359 * Default constructor.
2360 */
2362 JF1_t()
2363 {}
2364
2365
2366 /**
2367 * Constructor.
2368 *
2369 * \param f1 function
2370 */
2371 JSin(const JF1_t& f1) :
2372 JF1_t(f1)
2373 {}
2374
2375
2376 /**
2377 * Function value.
2378 *
2379 * \param x abscissa value
2380 * \return function value
2381 */
2382 double getValue(const double x) const
2383 {
2384 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2385
2386 return sin(u);
2387 }
2388
2389
2390 /**
2391 * Derivative value.
2392 *
2393 * \param x abscissa value
2394 * \return derivative value
2395 */
2396 double getDerivative(const double x) const
2397 {
2398 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2399 const double v = static_cast<const JF1_t&>(*this).getDerivative(x);
2400
2401 return v * cos(u);
2402 }
2403
2404
2405 /**
2406 * Get gradient.
2407 *
2408 * \param x abscissa value
2409 * \return gradient
2410 */
2411 JSin getGradient(const double x) const
2412 {
2413 JSin gradient;
2414
2415 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2416
2417 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(x);
2418 static_cast<JF1_t&>(gradient) *= cos(u);
2419
2420 return gradient;
2421 }
2422 };
2423
2424
2425 /**
2426 * Sine of function.
2427 *
2428 * \param f1 function
2429 * \return result
2430 */
2431 template<class JF1_t>
2432 JSin<JF1_t> Sin(const JF1_t& f1)
2433 {
2434 return JSin<JF1_t>(f1);
2435 }
2436
2437
2438 /**
2439 * Cosine of function.
2440 */
2441 template<class JF1_t = JX>
2442 struct JCos :
2443 public JMathlib < JCos<JF1_t> >,
2444 public JF1_t
2445 {
2446 using JMathlib< JCos<JF1_t> >::operator();
2447 using JMathlib< JCos<JF1_t> >::operator[];
2448
2449
2450 /**
2451 * Default constructor.
2452 */
2454 JF1_t()
2455 {}
2456
2457
2458 /**
2459 * Constructor.
2460 *
2461 * \param f1 function
2462 */
2463 JCos(const JF1_t& f1) :
2464 JF1_t(f1)
2465 {}
2466
2467
2468 /**
2469 * Function value.
2470 *
2471 * \param x abscissa value
2472 * \return function value
2473 */
2474 double getValue(const double x) const
2475 {
2476 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2477
2478 return cos(u);
2479 }
2480
2481
2482 /**
2483 * Derivative value.
2484 *
2485 * \param x abscissa value
2486 * \return derivative value
2487 */
2488 double getDerivative(const double x) const
2489 {
2490 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2491 const double v = static_cast<const JF1_t&>(*this).getDerivative(x);
2492
2493 return v * -sin(u);
2494 }
2495
2496
2497 /**
2498 * Get gradient.
2499 *
2500 * \param x abscissa value
2501 * \return gradient
2502 */
2503 JCos getGradient(const double x) const
2504 {
2505 JCos gradient;
2506
2507 const double u = static_cast<const JF1_t&>(*this).getValue(x);
2508
2509 static_cast<JF1_t&>(gradient) = static_cast<const JF1_t&>(*this).getGradient(x);
2510 static_cast<JF1_t&>(gradient) *= -sin(u);
2511
2512 return gradient;
2513 }
2514 };
2515
2516
2517 /**
2518 * Cosine of function.
2519 *
2520 * \param f1 function
2521 * \return result
2522 */
2523 template<class JF1_t>
2524 JCos<JF1_t> Cos(const JF1_t& f1)
2525 {
2526 return JCos<JF1_t>(f1);
2527 }
2528
2529
2530 /**
2531 * Exponent of function.
2532 */
2533 template<class JF1_t = JX>
2534 struct JExp :
2535 public JMathlib< JExp<JF1_t> >,
2536 public JF1_t
2537 {
2538 using JMathlib< JExp<JF1_t> >::operator();
2539 using JMathlib< JExp<JF1_t> >::operator[];
2540
2541
2542 /**
2543 * Default constructor.
2544 */
2546 JF1_t()
2547 {}
2548
2549
2550 /**
2551 * Constructor.
2552 *
2553 * \param f1 function
2554 */
2555 JExp(const JF1_t& f1) :
2556 JF1_t(f1)
2557 {}
2558
2559
2560 /**
2561 * Function value.
2562 *
2563 * \param x abscissa value
2564 * \return function value
2565 */
2566 double getValue(const double x) const
2567 {
2568 return exp(static_cast<const JF1_t&>(*this).getValue(x));
2569 }
2570
2571
2572 /**
2573 * Derivative value.
2574 *
2575 * \param x abscissa value
2576 * \return derivative value
2577 */
2578 double getDerivative(const double x) const
2579 {
2580 return static_cast<const JF1_t&>(*this).getDerivative(x) * getValue(x);
2581 }
2582
2583
2584 /**
2585 * Get gradient.
2586 *
2587 * \param x abscissa value
2588 * \return gradient
2589 */
2590 JExp getGradient(const double x) const
2591 {
2592 JExp gradient;
2593
2594 gradient = static_cast<const JF1_t&>(*this).getGradient(x);
2595 gradient *= getValue(x);
2596
2597 return gradient;
2598 }
2599 };
2600
2601
2602 /**
2603 * Exponent of zero degree polynomial function.
2604 */
2605 template<int ID_t>
2606 struct JExp< JPolynome<ID_t, 0> > :
2607 public JMathlib< JExp< JPolynome<ID_t, 0> > >,
2608 public JPolynome<ID_t, 0>
2609 {
2610 using JMathlib< JExp< JPolynome<ID_t, 0> > >::operator();
2611 using JMathlib< JExp< JPolynome<ID_t, 0> > >::operator[];
2612
2613
2614 /**
2615 * Default constructor.
2616 */
2618 JPolynome<ID_t, 0>()
2619 {}
2620
2621
2622 /**
2623 * Constructor.
2624 *
2625 * \param f1 function
2626 */
2628 JPolynome<ID_t, 0>(f1)
2629 {}
2630
2631
2632 /**
2633 * Function value.
2634 *
2635 * \return function value
2636 */
2637 double getValue(...) const
2638 {
2639 return exp(static_cast<const JPolynome<ID_t, 0>&>(*this).getValue());
2640 }
2641
2642
2643 /**
2644 * Derivative value.
2645 *
2646 * \return derivative value
2647 */
2648 double getDerivative(...) const
2649 {
2650 return static_cast<const JPolynome<ID_t, 0>&>(*this).getDerivative() * getValue();
2651 }
2652
2653
2654 /**
2655 * Get gradient.
2656 *
2657 * \return gradient
2658 */
2660 {
2661 JExp gradient;
2662
2663 gradient = static_cast<const JPolynome<ID_t, 0>&>(*this).getGradient();
2664 gradient *= getValue();
2665
2666 return gradient;
2667 }
2668 };
2669
2670
2671 /**
2672 * Exponent of function.
2673 *
2674 * \param f1 function
2675 * \return result
2676 */
2677 template<class JF1_t>
2678 JExp<JF1_t> Exp(const JF1_t& f1)
2679 {
2680 return JExp<JF1_t>(f1);
2681 }
2682
2683
2684 /**
2685 * Logarithm of function.
2686 */
2687 template<class JF1_t = JX>
2688 struct JLog :
2689 public JMathlib< JLog<JF1_t> >,
2690 public JF1_t
2691 {
2692 using JMathlib< JLog<JF1_t> >::operator();
2693 using JMathlib< JLog<JF1_t> >::operator[];
2694
2695
2696 /**
2697 * Default constructor.
2698 */
2700 JF1_t()
2701 {}
2702
2703
2704 /**
2705 * Constructor.
2706 *
2707 * \param f1 function
2708 */
2709 JLog(const JF1_t& f1) :
2710 JF1_t(f1)
2711 {}
2712
2713
2714 /**
2715 * Function value.
2716 *
2717 * \param x abscissa value
2718 * \return function value
2719 */
2720 double getValue(const double x) const
2721 {
2722 return log(static_cast<const JF1_t&>(*this).getValue(x));
2723 }
2724
2725
2726 /**
2727 * Derivative value.
2728 *
2729 * \param x abscissa value
2730 * \return derivative value
2731 */
2732 double getDerivative(const double x) const
2733 {
2734 return static_cast<const JF1_t&>(*this).getDerivative(x) / static_cast<const JF1_t&>(*this).getValue(x);
2735 }
2736
2737
2738 /**
2739 * Get gradient.
2740 *
2741 * \param x abscissa value
2742 * \return gradient
2743 */
2744 JLog getGradient(const double x) const
2745 {
2746 JLog gradient;
2747
2748 gradient = static_cast<const JF1_t&>(*this).getGradient(x);
2749 gradient /= (static_cast<const JF1_t&>(*this).getValue(x));
2750
2751 return gradient;
2752 }
2753 };
2754
2755
2756 /**
2757 * Logarithm of function.
2758 *
2759 * \param f1 function
2760 * \return result
2761 */
2762 template<class JF1_t>
2763 JLog<JF1_t> Log(const JF1_t& f1)
2764 {
2765 return JLog<JF1_t>(f1);
2766 }
2767}
2768
2769#endif
constexpr size_t getNumberOfParameters()
Get number of parameters.
Definition JMathlib.hh:135
void setParameters(JF1_t *f1, const double *values)
Set values of all parameters.
Definition JMathlib.hh:148
JPow< JF1_t::ID, JF1_t > Pow(const JF1_t &f1, const double alpha)
Power of function.
Definition JMathlib.hh:2248
static const JXn< 5 > X5
Function object for x^4;.
Definition JMathlib.hh:1615
JSqrt< JF1_t > Sqrt(const JF1_t &f1)
Square root of function.
Definition JMathlib.hh:2340
JExp< JF1_t > Exp(const JF1_t &f1)
Exponent of function.
Definition JMathlib.hh:2678
static const JXn< 3 > X3
Function object for x^2;.
Definition JMathlib.hh:1613
T pow(const T &x, const double y)
Power .
Definition JMath.hh:97
static const JXn< 4 > X4
Function object for x^3;.
Definition JMathlib.hh:1614
JCos< JF1_t > Cos(const JF1_t &f1)
Cosine of function.
Definition JMathlib.hh:2524
constexpr parameter_list< U, sizeof...(i)> convert(const parameter_list< V, sizeof...(i)> &parameters, const std::index_sequence< i... > &ls)
Auxiliary method to convert parameter list.
Definition JMathlib.hh:109
constexpr parameter_list< U, sizeof...(i)+1 > join(const parameter_list< V, sizeof...(i)> &parameters, const std::index_sequence< i... > &ls, double W::*parameter)
Auxiliary method to join parameter and list of parameters.
Definition JMathlib.hh:43
static const JXn< 2 > X2
Invalidate x^0.
Definition JMathlib.hh:1612
static const JX X
Definition JMathlib.hh:1551
JSin< JF1_t > Sin(const JF1_t &f1)
Sine of function.
Definition JMathlib.hh:2432
This name space includes all other name spaces (except KM3NETDAQ, KM3NET and ANTARES).
Definition log.hh:13
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:681
JAdd getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:694
JAdd()
Default constructor.
Definition JMathlib.hh:646
JAdd(const JF1_t &f1, const double value)
Constructor.
Definition JMathlib.hh:656
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:669
forward declaration for negation of function.
Definition JMathlib.hh:1100
JAdd getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:1157
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:1143
JAdd()
Default constructor.
Definition JMathlib.hh:1108
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:1130
JAdd(const JF1_t &f1, const JF2_t &f2)
Constructor.
Definition JMathlib.hh:1118
Auxiliary base class for mathematical operations on parameters of function.
Definition JMathlib.hh:163
JF1_t & div(const double factor)
Scale function.
Definition JMathlib.hh:233
JF1_t & mul(const double factor)
Scale function.
Definition JMathlib.hh:217
JF1_t & add(const JF1_t &f1)
Add function.
Definition JMathlib.hh:185
friend JF1_t & operator+=(JF1_t &function, const JF1_t &value)
Add function.
Definition JMathlib.hh:250
friend JF1_t & operator/=(JF1_t &function, const double factor)
Scale function.
Definition JMathlib.hh:289
friend JF1_t & operator*=(JF1_t &function, const double factor)
Scale function.
Definition JMathlib.hh:276
JF1_t & sub(const JF1_t &f1)
Subtract function.
Definition JMathlib.hh:201
JF1_t & negate()
Negate function.
Definition JMathlib.hh:169
friend JF1_t & operator-=(JF1_t &function, const JF1_t &value)
Subtract function.
Definition JMathlib.hh:263
Cosine of function.
Definition JMathlib.hh:2445
JCos(const JF1_t &f1)
Constructor.
Definition JMathlib.hh:2463
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:2488
JCos getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:2503
double getValue(const double x) const
Function value.
Definition JMathlib.hh:2474
JCos()
Default constructor.
Definition JMathlib.hh:2453
JDiv(const JF1_t &f1, const double value)
Constructor.
Definition JMathlib.hh:888
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:901
JDiv getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:926
JDiv()
Default constructor.
Definition JMathlib.hh:878
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:913
forward declaration for multiplication of fuction.
Definition JMathlib.hh:1331
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:1361
JDiv getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:1391
JDiv()
Default constructor.
Definition JMathlib.hh:1339
JDiv(const JF1_t &f1, const JF2_t &f2)
Constructor.
Definition JMathlib.hh:1349
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:1374
double getDerivative(...) const
Derivative value.
Definition JMathlib.hh:2648
double getValue(...) const
Function value.
Definition JMathlib.hh:2637
JExp(const JPolynome< ID_t, 0 > &f1)
Constructor.
Definition JMathlib.hh:2627
JExp getGradient(...) const
Get gradient.
Definition JMathlib.hh:2659
Exponent of function.
Definition JMathlib.hh:2537
JExp()
Default constructor.
Definition JMathlib.hh:2545
JExp getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:2590
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:2578
double getValue(const double x) const
Function value.
Definition JMathlib.hh:2566
JExp(const JF1_t &f1)
Constructor.
Definition JMathlib.hh:2555
forward declaration for division of fuction.
Definition JMathlib.hh:1415
JFn()
Default constructor.
Definition JMathlib.hh:1423
JFn(const JF1_t &f1, const int N)
Constructor.
Definition JMathlib.hh:1435
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:1462
JFn getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:1478
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:1448
JGauss(const double center, const double sigma)
Constructor.
Definition JMathlib.hh:2061
JGauss getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:2103
JGauss()
Default constructor.
Definition JMathlib.hh:2049
double getValue(const double x) const
Function value.
Definition JMathlib.hh:2074
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:2088
double get(const double u) const
Get ordinate value.
Definition JMathlib.hh:2129
Gauss function object.
Definition JMathlib.hh:1941
double sigma
sigma
Definition JMathlib.hh:2017
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:1987
JGauss()
Default constructor.
Definition JMathlib.hh:1948
double center
center
Definition JMathlib.hh:2016
static constexpr parameter_list< JGauss, 2 > parameters
Definition JMathlib.hh:2019
double getValue(const double x) const
Function value.
Definition JMathlib.hh:1973
JGauss_t gradient
Definition JGauss.hh:289
JGauss getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:2002
double get(const double u) const
Get ordinate value.
Definition JGauss.hh:284
JGauss(const double center, const double sigma)
Constructor.
Definition JMathlib.hh:1960
Logarithm of function.
Definition JMathlib.hh:2691
double getValue(const double x) const
Function value.
Definition JMathlib.hh:2720
JLog getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:2744
JLog()
Default constructor.
Definition JMathlib.hh:2699
JLog(const JF1_t &f1)
Constructor.
Definition JMathlib.hh:2709
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:2732
forward declaration for pointer to function.
Definition JMathlib.hh:323
friend JMul< JF1_t, JF2_t > operator*(const JF1_t &f1, const JF2_t &f2)
Multiplication of two functions.
Definition JMathlib.hh:488
friend JDiv< JF1_t, JF2_t > operator/(const JF1_t &f1, const JF2_t &f2)
Division of two functions.
Definition JMathlib.hh:502
friend JAdd< JNegate< JF1_t > > operator-(const double value, const JF1_t &f1)
Subtraction of constant value.
Definition JMathlib.hh:407
friend JFn< JF1_t > operator^(const JF1_t &f1, int N)
Power-of operator.
Definition JMathlib.hh:515
double operator[](const size_t i) const
Get value of parameter at given index.
Definition JMathlib.hh:539
double & operator[](const size_t i)
Get value of parameter at given index.
Definition JMathlib.hh:551
friend JAdd< JF1_t > operator+(const double value, const JF1_t &f1)
Addition of constant value.
Definition JMathlib.hh:381
friend JSub< JF1_t > operator-(const JF1_t &f1, const double value)
Subtraction of constant value.
Definition JMathlib.hh:394
friend const JF1_t & operator+(const JF1_t &function)
Affirm operator.
Definition JMathlib.hh:343
friend JMul< JF1_t > operator*(const double value, const JF1_t &f1)
Multiplication of constant value.
Definition JMathlib.hh:433
friend JSub< JF1_t, JF2_t > operator-(const JF1_t &f1, const JF2_t &f2)
Subtraction of two functions.
Definition JMathlib.hh:474
friend JDiv< JF1_t > operator/(const JF1_t &f1, const double value)
Division of constant value.
Definition JMathlib.hh:446
double operator()(const Args &...args) const
Function value.
Definition JMathlib.hh:331
friend JAdd< JF1_t > operator+(const JF1_t &f1, const double value)
Addition of constant value.
Definition JMathlib.hh:368
friend JPf< JF1_t > operator&(const JF1_t &f1)
Address-of operator.
Definition JMathlib.hh:527
friend JNegate< JF1_t > operator-(const JF1_t &function)
Negate operator.
Definition JMathlib.hh:355
friend JAdd< JF1_t, JF2_t > operator+(const JF1_t &f1, const JF2_t &f2)
Addition of two functions.
Definition JMathlib.hh:460
friend JMul< JF1_t > operator*(const JF1_t &f1, const double value)
Multiplication of constant value.
Definition JMathlib.hh:420
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:823
JMul(const JF1_t &f1, const double value)
Constructor.
Definition JMathlib.hh:810
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:835
JMul getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:848
JMul()
Default constructor.
Definition JMathlib.hh:800
forward declaration for subtraction of fuction.
Definition JMathlib.hh:1253
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:1283
JMul()
Default constructor.
Definition JMathlib.hh:1261
JMul(const JF1_t &f1, const JF2_t &f2)
Constructor.
Definition JMathlib.hh:1271
JMul getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:1310
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:1296
Negate of function.
Definition JMathlib.hh:565
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:594
JNegate()
Default constructor.
Definition JMathlib.hh:573
JNegate(const JF1_t &f1)
Constructor.
Definition JMathlib.hh:582
JNegate getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:619
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:606
JPair(const JF1_t &f1, const JF2_t &f2)
Constructor.
Definition JMathlib.hh:1052
JPair(const JF1_t &f1, const JF2_t &f2)
Constructor.
Definition JMathlib.hh:1023
JPair(const JF1_t &f1, const JF2_t &f2)
Constructor.
Definition JMathlib.hh:994
Auxiliary data structure for pair of functions.
Definition JMathlib.hh:1066
JPair_t()
Default constructor.
Definition JMathlib.hh:1077
JPair_t(const JF1_t &f1, const JF2_t &f2)
Constructor.
Definition JMathlib.hh:1087
Auxiliary data structure for pair of functions.
Definition JMathlib.hh:950
static constexpr parameter_list< JPair, JF1_t::parameters.size()+JF2_t::parameters.size()> parameters
Definition JMathlib.hh:969
JPair(const JF1_t &f1, const JF2_t &f2)
Constructor.
Definition JMathlib.hh:964
JPair()
Default constructor.
Definition JMathlib.hh:954
forward declaration for fixed power of function.
Definition JMathlib.hh:1633
const JF1_t * f1
Definition JMathlib.hh:1698
JPf getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:1688
JPf()
Default constructor.
Definition JMathlib.hh:1641
JPf(const JF1_t *f1)
Constructor.
Definition JMathlib.hh:1651
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:1663
static constexpr parameter_list< JPf, 0 > parameters
Definition JMathlib.hh:1695
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:1675
Termination class for polynomial function.
Definition JMathlib.hh:1829
JPolynome getGradient(...) const
Get gradient.
Definition JMathlib.hh:1892
double getValue(...) const
Function value.
Definition JMathlib.hh:1870
double getDerivative(...) const
Derivative value.
Definition JMathlib.hh:1881
JPolynome()
Default constructor.
Definition JMathlib.hh:1838
void set(const double x)
Recursive method for setting values.
Definition JMathlib.hh:1911
JPolynome(const std::array< double, 1 > &args)
Constructor.
Definition JMathlib.hh:1858
JPolynome(const double a)
Constructor.
Definition JMathlib.hh:1848
JPolynome_t & mul(const double factor)
Scale polynome.
Definition JPolynome.hh:113
JPolynome_t & sub(const JPolynome_t &polynome)
Subtract polynome.
Definition JPolynome.hh:93
JPolynome_t & add(const JPolynome_t &polynome)
Add polynome.
Definition JPolynome.hh:73
Recursive template class for polynomial function.
Definition JPolynome.hh:165
static const size_t NUMBER_OF_DEGREES
Definition JMathlib.hh:1713
JPolynome()
Default constructor.
Definition JMathlib.hh:1727
JPolynome(const Args &...args)
Constructor.
Definition JMathlib.hh:1738
double getValue(const double x) const
Function value.
Definition JMathlib.hh:1765
void set(const double x, const Args &...args)
Recursive method for setting values.
Definition JMathlib.hh:1812
JPolynome(const std::array< double, N+1 > &args)
Constructor.
Definition JMathlib.hh:1750
JPolynome getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:1789
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:1777
static constexpr parameter_list< JPolynome, N+1 > parameters
Definition JMathlib.hh:1802
Power of function.
Definition JMathlib.hh:2145
double getValue(const double x) const
Function value.
Definition JMathlib.hh:2190
JPow(const JF1_t &f1, const double alpha)
Constructor.
Definition JMathlib.hh:2178
double alpha
f(x)^alpha
Definition JMathlib.hh:2234
JPow getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:2219
static constexpr parameter_list< JPow, 1 > parameters
Definition JMathlib.hh:2236
JPow(const double alpha)
Constructor.
Definition JMathlib.hh:2166
JPow()
Default constructor.
Definition JMathlib.hh:2155
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:2204
Sine of function.
Definition JMathlib.hh:2353
JSin()
Default constructor.
Definition JMathlib.hh:2361
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:2396
double getValue(const double x) const
Function value.
Definition JMathlib.hh:2382
JSin getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:2411
JSin(const JF1_t &f1)
Constructor.
Definition JMathlib.hh:2371
Square root of function.
Definition JMathlib.hh:2261
JSqrt()
Default constructor.
Definition JMathlib.hh:2269
double getValue(const double x) const
Function value.
Definition JMathlib.hh:2290
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:2304
JSqrt getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:2319
JSqrt(const JF1_t &f1)
Constructor.
Definition JMathlib.hh:2279
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:746
JSub getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:771
JSub()
Default constructor.
Definition JMathlib.hh:723
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:758
JSub(const JF1_t &f1, const double value)
Constructor.
Definition JMathlib.hh:733
forward declaration for addition of fuction.
Definition JMathlib.hh:1176
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:1219
double getValue(const Args &...args) const
Function value.
Definition JMathlib.hh:1206
JSub getGradient(const Args &...args) const
Get gradient.
Definition JMathlib.hh:1233
JSub()
Default constructor.
Definition JMathlib.hh:1184
JSub(const JF1_t &f1, const JF2_t &f2)
Constructor.
Definition JMathlib.hh:1194
double getValue(const double x) const
Function value.
Definition JMathlib.hh:1516
JX getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:1540
JX()
Default constructor.
Definition JMathlib.hh:1506
static constexpr parameter_list< JX, 0 > parameters
Definition JMathlib.hh:1547
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:1528
Function object for x;.
Definition JMathlib.hh:1561
double getValue(const double x) const
Function value.
Definition JMathlib.hh:1575
double getDerivative(const double x) const
Derivative value.
Definition JMathlib.hh:1587
JXn()
Default constructor.
Definition JMathlib.hh:1565
JXn getGradient(const double x) const
Get gradient.
Definition JMathlib.hh:1599
static constexpr parameter_list< JXn, 0 > parameters
Definition JMathlib.hh:1606