File indexing completed on 2024-05-12 03:47:52

0001 /*
0002     File                 : nsl_math.h
0003     Project              : LabPlot
0004     Description          : NSL math functions
0005     --------------------------------------------------------------------
0006     SPDX-FileCopyrightText: 2018-2024 Stefan Gerlach <stefan.gerlach@uni.kn>
0007     SPDX-License-Identifier: GPL-2.0-or-later
0008 */
0009 
0010 #ifndef NSL_MATH_H
0011 #define NSL_MATH_H
0012 
0013 #undef __BEGIN_DECLS
0014 #undef __END_DECLS
0015 #ifdef __cplusplus
0016 #define __BEGIN_DECLS extern "C" {
0017 #define __END_DECLS }
0018 #else
0019 #define __BEGIN_DECLS /* empty */
0020 #define __END_DECLS /* empty */
0021 #endif
0022 __BEGIN_DECLS
0023 
0024 #include <stdbool.h>
0025 
0026 #define M_PI_180 (M_PI / 180.)
0027 #define M_180_PI (180. / M_PI)
0028 
0029 typedef enum round_method { Round, Floor, Ceil, Trunc } round_method;
0030 
0031 /*
0032  * more intelligent comparison of doubles,
0033  * taken from Knuth's "The art of computer programming"
0034  */
0035 bool nsl_math_approximately_equal(double a, double b);
0036 bool nsl_math_essentially_equal(double a, double b);
0037 bool nsl_math_definitely_greater_than(double a, double b);
0038 bool nsl_math_definitely_less_than(double a, double b);
0039 bool nsl_math_approximately_equal_eps(double a, double b, double epsilon);
0040 bool nsl_math_essentially_equal_eps(double a, double b, double epsilon);
0041 bool nsl_math_definitely_greater_than_eps(double a, double b, double epsilon);
0042 bool nsl_math_definitely_less_than_eps(double a, double b, double epsilon);
0043 
0044 /*
0045  * split x into fraction and (optional) exponent where x = fraction * 10^e
0046  */
0047 double nsl_math_frexp10(double x, int* e);
0048 
0049 /* returns decimal places of signed value
0050  * 0.1 -> 1, 0.06 -> 2, 23 -> -1, 100 -> -2
0051  */
0052 int nsl_math_decimal_places(double value);
0053 
0054 /* return decimal places of signed value rounded to one digit
0055  * 0.1 -> 1, 0.006 -> 2, 0.8 -> 0, 12 -> -1, 520 -> -3
0056  */
0057 int nsl_math_rounded_decimals(double value);
0058 
0059 /* nsl_math_rounded_decimals() but max 'max'
0060  */
0061 int nsl_math_rounded_decimals_max(double value, int max);
0062 
0063 /* round double value to n decimal places
0064  * 1234.556 & n = 3 -> 1234.556, 0.001234 & n = 4 -> 0.0012
0065  */
0066 double nsl_math_round_places(double value, int n);
0067 double nsl_math_floor_places(double value, int n);
0068 double nsl_math_ceil_places(double value, int n);
0069 double nsl_math_trunc_places(double value, int n);
0070 double nsl_math_places(double value, int n, int method);
0071 
0072 /* round double value to precision p in scientific notation
0073  * 1234.5 & p = 2 -> 1230 (1.23e3), 0.012345 & p = 2 -> 0.0123 (1.23e-2)
0074  * p <= 0 : order of magnitude (power of 10)
0075  */
0076 double nsl_math_round_precision(double value, int p);
0077 /* same as above but for any base x
0078  * p <= 0 : power of x
0079  */
0080 double nsl_math_round_basex(double value, int p, double base);
0081 
0082 /* round double value 'value' to multiple of 'multiple'
0083  * (2.5, 2) -> 2,2,4,2 (4.5, 3) -> 6,3,6,3
0084  */
0085 double nsl_math_round_multiple(double value, double multiple);
0086 double nsl_math_floor_multiple(double value, double multiple);
0087 double nsl_math_ceil_multiple(double value, double multiple);
0088 double nsl_math_trunc_multiple(double value, double multiple);
0089 double nsl_math_multiple(double value, double multiple, round_method method);
0090 
0091 __END_DECLS
0092 
0093 #endif /* NSL_MATH_H */