VirtualFluids 0.2.0
Parallel CFD LBM Solver
Loading...
Searching...
No Matches
UbMath.h
Go to the documentation of this file.
1//=======================================================================================
2// ____ ____ __ ______ __________ __ __ __ __
3// \ \ | | | | | _ \ |___ ___| | | | | / \ | |
4// \ \ | | | | | |_) | | | | | | | / \ | |
5// \ \ | | | | | _ / | | | | | | / /\ \ | |
6// \ \ | | | | | | \ \ | | | \__/ | / ____ \ | |____
7// \ \ | | |__| |__| \__\ |__| \________/ /__/ \__\ |_______|
8// \ \ | | ________________________________________________________________
9// \ \ | | | ______________________________________________________________|
10// \ \| | | | __ __ __ __ ______ _______
11// \ | | |_____ | | | | | | | | | _ \ / _____)
12// \ | | _____| | | | | | | | | | | \ \ \_______
13// \ | | | | |_____ | \_/ | | | | |_/ / _____ |
14// \ _____| |__| |________| \_______/ |__| |______/ (_______/
15//
16// This file is part of VirtualFluids. VirtualFluids is free software: you can
17// redistribute it and/or modify it under the terms of the GNU General Public
18// License as published by the Free Software Foundation, either version 3 of
19// the License, or (at your option) any later version.
20//
21// VirtualFluids is distributed in the hope that it will be useful, but WITHOUT
22// ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
23// FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
24// for more details.
25//
26// SPDX-License-Identifier: GPL-3.0-or-later
27// SPDX-FileCopyrightText: Copyright © VirtualFluids Project contributors, see AUTHORS.md in root folder
28//
33//=======================================================================================
34#ifndef UBMATH_H
35#define UBMATH_H
36
39#include <cassert>
40#include <cmath>
41#include <iostream>
42#include <limits>
43
44namespace ub_math
45{
46extern const double PI;
47
49// Hilfsfunktion fuer Genauigkeit
50template <typename T>
51struct Epsilon {
52};
53
55// SPECIALIZATIONS von Epsilon
57template <>
58struct Epsilon<double> {
59 static inline double val() { return 1.0E-11; }
60};
61template <>
62struct Epsilon<float> {
63 static inline float val() { return 1.0E-7f; }
64};
65template <>
67 static inline long double val() { return 1.0E-15; }
68};
69template <>
70struct Epsilon<int> {
71 static inline int val() { return 0; }
72};
73
74/*=======================================================*/
75// -------------------------------------------------------------------------------------------------
76// Funktion berechnet den Logarithmus einer Zahl z bzgl. der Basis b
77// -------------------------------------------------------------------------------------------------
78template <typename T>
79inline T log(const T &z, const T &base)
80{
81 if (::log(base) == 0)
82 return 1.0f;
83 return ::log(z) / ::log(base);
84}
85/*=======================================================*/
86// double x = ub_math::getNegativeInfinity<double>();
87template <typename T>
89{
90 // assert(std::numeric_limits<T>::has_infinity);
91 UB_STATIC_ASSERT(std::numeric_limits<T>::has_infinity);
92 return -std::numeric_limits<T>::infinity();
93}
94/*=======================================================*/
95// double x = ub_math::getPositiveInfinity<double>();
96template <typename T>
98{
99 // assert(std::numeric_limits<T>::has_infinity);
100 UB_STATIC_ASSERT(std::numeric_limits<T>::has_infinity);
101 return std::numeric_limits<T>::infinity();
102}
103/*=======================================================*/
104// double x; bool b = ub_math::isInfinity(x);
105template <typename T>
106inline bool isInfinity(const T &value)
107{
108 if (value == getNegativeInfinity<T>())
109 return true;
110 if (value == getPositiveInfinity<T>())
111 return true;
112 return false;
113}
114/*=======================================================*/
115// double x = ub_math::getNaN<double>(x);
116template <typename T>
117inline T getNaN()
118{
119 UB_STATIC_ASSERT(std::numeric_limits<T>::has_quiet_NaN);
120 return std::numeric_limits<T>::quiet_NaN();
121}
122/*=======================================================*/
123// double x; bool b = ub_math::isNaN(x);
124// x!=x liefert bei #QNAN "true"!
125template <typename T>
126inline bool isNaN(const T &x)
127{
128 UB_STATIC_ASSERT(std::numeric_limits<T>::has_quiet_NaN);
129 return (x != x);
130}
131/*=======================================================*/
132template <typename T>
134{
135 return Epsilon<T>::val();
136}
137/*=======================================================*/
138template <typename T>
139inline bool zero(const T &value)
140{
141 return std::fabs(value) < Epsilon<T>::val();
142 // return value >= -ub_math::EPSILON && value <= ub_math::EPSILON;
143}
144/*=======================================================*/
145// spezialisierung fuer ints
146template <>
147inline bool zero(const int &value)
148{
149 return value == 0;
150}
151/*=======================================================*/
152template <typename T1, typename T2>
153inline bool zero(const T1 &value1, const T2 &value2)
154{
155 return !(!ub_math::zero(value1) || !ub_math::zero(value2));
156}
157/*=======================================================*/
158template <typename T1, typename T2, typename T3>
159inline bool zero(const T1 &value1, const T2 &value2, const T3 &value3)
160{
161 return !(!ub_math::zero(value1) || !ub_math::zero(value2, value3));
162}
163/*=======================================================*/
164template <typename T>
165inline bool negative(const T &value)
166{
167 return value < -Epsilon<T>::val();
168}
169/*=======================================================*/
170template <typename T>
171inline bool nonPositive(const T &value)
172{
174}
175/*=======================================================*/
176template <typename T>
177inline bool positive(const T &value)
178{
179 return value > +Epsilon<T>::val();
180}
181/*=======================================================*/
182template <typename T>
183inline bool nonNegative(const T &value)
184{
185 return value >= -Epsilon<T>::val();
186}
187/*=======================================================*/
188template <typename T1, typename T2>
189inline bool equal(const T1 &value, const T2 &reference)
190{
191 using High = typename UbEqualTrait<T1, T2>::High;
192 return std::fabs(value - reference) < Epsilon<High>::val();
193}
194/*=======================================================*/
195template <typename T1, typename T2, typename T3>
196inline bool equal(const T1 &val1, const T2 &val2, const T3 &val3)
197{
199}
200/*=======================================================*/
201template <typename T1, typename T2>
202inline bool less(const T1 &value, const T2 &reference)
203{
204 using High = typename UbEqualTrait<T1, T2>::High;
205 return value < reference - Epsilon<High>::val();
206}
207/*=======================================================*/
208template <typename T1, typename T2>
209inline bool lessEqual(const T1 &value, const T2 &reference)
210{
211 using High = typename UbEqualTrait<T1, T2>::High;
213}
214/*=======================================================*/
215template <typename T1, typename T2>
216inline bool greater(const T1 &value, const T2 &reference)
217{
218 using High = typename UbEqualTrait<T1, T2>::High;
219 return value > reference + Epsilon<High>::val();
220}
221/*=======================================================*/
222template <typename T1, typename T2>
223inline bool greaterEqual(const T1 &value, const T2 &reference)
224{
225 using High = typename UbEqualTrait<T1, T2>::High;
226 return value >= reference - Epsilon<High>::val();
227}
228/*=======================================================*/
229template <typename T>
230inline T round(const T &value, const int &decimalPlaces)
231{
232 return static_cast<T>(floor(value * pow(10.0, decimalPlaces) + 0.5) * pow(10.0, -decimalPlaces));
233}
234/*=======================================================*/
235template <typename T>
236inline int integerRounding(const T &value)
237{
238 return static_cast<int>(ub_math::zero(value) ? 0 : ((value < 0.0) ? (value - 0.5) : (value + 0.5)));
239}
240/*=======================================================*/
241template <typename T>
242inline T getRad(const T &degrees)
243{
244 return degrees * static_cast<T>(ub_math::PI / 180.0);
245}
246/*=======================================================*/
247template <typename T>
248inline T getDegrees(const T &rad)
249{
250 return rad * static_cast<T>(ub_math::PI / 180.0);
251}
252/*=======================================================*/
253// aus wildmagic
254template <typename T>
255inline T ACos(const T &fValue)
256{
257 if (-1.0 < fValue) {
258 if (fValue < 1.0)
259 return static_cast<T>(acos(fValue));
260 else
261 return static_cast<T>(0.0);
262 } else
263 return static_cast<T>(PI);
264}
265/*=======================================================*/
266template <typename T>
267inline T ASin(const T &fValue)
268{
269 double HALF_PI = 0.5 * ub_math::PI;
270 if (-1.0 < fValue) {
271 if (fValue < 1.0)
272 return static_cast<T>(asin(fValue));
273 else
274 return static_cast<T>(HALF_PI);
275 } else
276 return -static_cast<T>(HALF_PI);
277}
278/*=======================================================*/
279template <typename T>
280inline T invSqrt(const T &fValue)
281{
282 return static_cast<T>(1.0 / sqrt(fValue));
283}
284
285/*=======================================================*/
294template <typename T1, typename T2, typename T3, typename T4>
295inline bool less2(const T1 &value1, const T2 &value2, T3 toBeLessAs1, T4 toBeLessAs2)
296{
297 return (less(value1, toBeLessAs1) && less(value1, toBeLessAs2) && less(value2, toBeLessAs1) &&
298 less(value2, toBeLessAs2));
299}
300/*=======================================================*/
301template <typename T1, typename T2, typename T3, typename T4>
302inline bool greater2(const T1 &value1, const T2 &value2, T3 toBeGreaterAs1, T4 toBeGreaterAs2)
303{
304 return (greater(value1, toBeGreaterAs1) && greater(value1, toBeGreaterAs2) && greater(value2, toBeGreaterAs1) &&
305 greater(value2, toBeGreaterAs2));
306}
307/*=======================================================*/
308template <typename T1, typename T2, typename T3>
309inline bool inClosedInterval(const T1 &value, const T2 &threshold1, const T3 &threshold2)
310{
311 if (threshold1 < threshold2) {
312 return (greaterEqual(value, threshold1) && lessEqual(value, threshold2));
313 }
314
315 return (greaterEqual(value, threshold2) && lessEqual(value, threshold1));
316}
317/*=======================================================*/
318template <typename T1, typename T2, typename T3>
319inline bool inOpenInterval(const T1 &value, const T2 &threshold1, const T3 &threshold2)
320{
321 if (threshold1 < threshold2) {
322 return (greater(value, threshold1) && less(value, threshold2));
323 }
324
325 return (greater(value, threshold2) && less(value, threshold1));
326}
327/*=======================================================*/
328template <typename T1, typename T2, typename T3>
329inline double adaptToClosedInterval(const T1 &value, const T2 &threshold1, const T3 &threshold2)
330{
331 if (threshold1 < threshold2) {
332 if (less(value, threshold1))
333 return threshold1;
334 else if (greater(value, threshold2))
335 return threshold2;
336 } else {
337 if (less(value, threshold2))
338 return threshold2;
339 else if (greater(value, threshold1))
340 return threshold1;
341 }
342 return value;
343}
344/*=======================================================*/
345// -------------------------------------------------------------------------------------------------
346// Funktion berechnet den groessten gemeinsamen Teiler zweier Zahlen (MK)
347// -------------------------------------------------------------------------------------------------
348/*=======================================================*/
349inline int calcGgt(int val1, int val2)
350{
351 if (val1 < val2)
352 std::swap(val1, val2);
353 int ggt = val2;
354 while (ggt > 1) {
355 if ((val1 % ggt) == 0 && (val2 % ggt) == 0)
356 break;
357
358 ggt -= 1;
359 }
360 return ggt;
361}
362/*=======================================================*/
363// -------------------------------------------------------------------------------------------------
364// Funktion berechnet den groessten gemeinsamen Teiler von drei Zahlen (MK)
365// -------------------------------------------------------------------------------------------------
366inline int calcGgt(int val1, const int &val2, int val3) { return ub_math::calcGgt(ub_math::calcGgt(val1, val2), val3); }
367/*=======================================================*/
368// returns the max of c2 values
369// to avoid errors at mixed argument-types use: double myMax = max<double>(2,2.3);
370template <typename T>
371inline const T &max(const T &a1, const T &a2)
372{
373 return (a1 < a2) ? a2 : a1;
374}
375/*=======================================================*/
376template <typename T>
377inline const T &max(const T &a1, const T &a2, const T &a3)
378{
379 return max(max(a1, a2), a3);
380}
381/*=======================================================*/
382template <typename T>
383inline const T &max(const T &a1, const T &a2, const T &a3, const T &a4)
384{
385 return max(max(max(a1, a2), a3), a4);
386}
387/*=======================================================*/
388template <typename T>
389inline const T &min(const T &a1, const T &a2)
390{
391 return (a1 < a2) ? a1 : a2;
392}
393/*=======================================================*/
394template <typename T>
395inline const T &min(const T &a1, const T &a2, const T &a3)
396{
397 return min(min(a1, a2), a3);
398}
399/*=======================================================*/
400template <typename T>
401inline const T &min(const T &a1, const T &a2, const T &a3, const T &a4)
402{
403 return min(min(min(a1, a2), a3), a4);
404
405 // double tmp = a1;
406 // if(tmp>a2) tmp=a2;
407 // if(tmp>a3) tmp=a3;
408 // if(tmp>a4) tmp=a4;
409 // return tmp;
410}
411template <typename T, typename U>
412constexpr T lerp(const T& a, const T& b, const U& t)
413{
414 return a + t * (b - a);
415}
416
417template <typename T, typename U>
418constexpr T lerp2(const T& a, const T& b, const T& c, const T& d, const U& t, const U& u)
419{
420 return lerp(lerp(a, b, t), lerp(c, d, t), u);
421}
422
423template <typename T, typename U>
424constexpr T lerp3(const T& a, const T& b, const T& c, const T& d, const T& e, const T& f, const T& g, const T& h, const U& t,
425 const U& u, const U& v)
426{
427 return lerp(lerp2(a, b, c, d, t, u), lerp2(e, f, g, h, t, u), v);
428}
429} // namespace ub_math
430
431#endif
432
std::shared_ptr< T > SPtr
@ z
Definition Axis.h:44
@ x
Definition Axis.h:42
#define UB_STATIC_ASSERT(expr)
Definition UbSystem.h:527
T getDegrees(const T &rad)
Definition UbMath.h:248
T ASin(const T &fValue)
Definition UbMath.h:267
bool greaterEqual(const T1 &value, const T2 &reference)
Definition UbMath.h:223
const double PI
T getNaN()
Definition UbMath.h:117
T getPositiveInfinity()
Definition UbMath.h:97
bool isInfinity(const T &value)
Definition UbMath.h:106
const T & min(const T &a1, const T &a2)
Definition UbMath.h:389
int integerRounding(const T &value)
Definition UbMath.h:236
T log(const T &z, const T &base)
Definition UbMath.h:79
T round(const T &value, const int &decimalPlaces)
Definition UbMath.h:230
constexpr T lerp2(const T &a, const T &b, const T &c, const T &d, const U &t, const U &u)
Definition UbMath.h:418
T getRad(const T &degrees)
Definition UbMath.h:242
bool lessEqual(const T1 &value, const T2 &reference)
Definition UbMath.h:209
T invSqrt(const T &fValue)
Definition UbMath.h:280
bool equal(const T1 &value, const T2 &reference)
Definition UbMath.h:189
bool positive(const T &value)
Definition UbMath.h:177
bool nonPositive(const T &value)
Definition UbMath.h:171
int calcGgt(int val1, int val2)
Definition UbMath.h:349
bool negative(const T &value)
Definition UbMath.h:165
T getNegativeInfinity()
Definition UbMath.h:88
bool greater2(const T1 &value1, const T2 &value2, T3 toBeGreaterAs1, T4 toBeGreaterAs2)
Definition UbMath.h:302
const T & max(const T &a1, const T &a2)
Definition UbMath.h:371
bool less2(const T1 &value1, const T2 &value2, T3 toBeLessAs1, T4 toBeLessAs2)
Definition UbMath.h:295
constexpr T lerp(const T &a, const T &b, const U &t)
Definition UbMath.h:412
bool greater(const T1 &value, const T2 &reference)
Definition UbMath.h:216
bool inClosedInterval(const T1 &value, const T2 &threshold1, const T3 &threshold2)
Definition UbMath.h:309
bool isNaN(const T &x)
Definition UbMath.h:126
T getEqualityEpsilon()
Definition UbMath.h:133
T ACos(const T &fValue)
Definition UbMath.h:255
bool inOpenInterval(const T1 &value, const T2 &threshold1, const T3 &threshold2)
Definition UbMath.h:319
constexpr T lerp3(const T &a, const T &b, const T &c, const T &d, const T &e, const T &f, const T &g, const T &h, const U &t, const U &u, const U &v)
Definition UbMath.h:424
bool zero(const T &value)
Definition UbMath.h:139
double adaptToClosedInterval(const T1 &value, const T2 &threshold1, const T3 &threshold2)
Definition UbMath.h:329
bool nonNegative(const T &value)
Definition UbMath.h:183
bool less(const T1 &value, const T2 &reference)
Definition UbMath.h:202
static double val()
Definition UbMath.h:59
static float val()
Definition UbMath.h:63
static int val()
Definition UbMath.h:71
static long double val()
Definition UbMath.h:67