optimize the interface with python
[liba.git] / src / mf.c
blob1f52779b0d3bd75b747faaa31d7f3ea4de12f9db
1 #include "a/math.h"
2 #include "a/mf.h"
4 a_float a_mf_gauss(a_float x, a_float sigma, a_float c)
6 return a_float_exp(a_float_pow((x - c) / sigma, 2) / -2);
9 a_float a_mf_gauss2(a_float x, a_float sigma1, a_float c1, a_float sigma2, a_float c2)
11 if (x < c1)
13 x = a_mf_gauss(x, sigma1, c1);
15 else if (x > c2)
17 x = a_mf_gauss(x, sigma2, c2);
19 else // c1 <= x <= c2
21 x = 1;
23 return x;
26 a_float a_mf_gbell(a_float x, a_float a, a_float b, a_float c)
28 return 1 / (a_float_pow(a_float_abs((x - c) / a), 2 * b) + 1);
31 a_float a_mf_sig(a_float x, a_float a, a_float c)
33 return 1 / (a_float_exp((c - x) * a) + 1);
36 a_float a_mf_dsig(a_float x, a_float a1, a_float c1, a_float a2, a_float c2)
38 return a_mf_sig(x, a1, c1) - a_mf_sig(x, a2, c2);
41 a_float a_mf_psig(a_float x, a_float a1, a_float c1, a_float a2, a_float c2)
43 return a_mf_sig(x, a1, c1) * a_mf_sig(x, a2, c2);
46 a_float a_mf_trap(a_float x, a_float a, a_float b, a_float c, a_float d)
48 if (x < b)
50 if (x > a) // a < x <= b
52 x = (x - a) / (b - a);
54 else // x <= a
56 x = 0;
59 else if (x > c)
61 if (x < d) // c <= x < d
63 x = (d - x) / (d - c);
65 else // d <= x
67 x = 0;
70 else // b <= x <= c
72 x = 1;
74 return x;
77 a_float a_mf_tri(a_float x, a_float a, a_float b, a_float c)
79 if (x < b)
81 if (x > a) // a < x <= b
83 x = (x - a) / (b - a);
85 else // x <= a
87 x = 0;
90 else
92 if (x < c) // b <= x < c
94 x = (c - x) / (c - b);
96 else // c <= x
98 x = 0;
101 return x;
104 a_float a_mf_lins(a_float x, a_float a, a_float b)
106 if (x < a)
108 x = 0;
110 else if (x > b)
112 x = 1;
114 else // a <= x <= b
116 x = (x - a) / (b - a);
118 return x;
121 a_float a_mf_linz(a_float x, a_float a, a_float b)
123 if (x < a)
125 x = 1;
127 else if (x > b)
129 x = 0;
131 else // a <= x <= b
133 x = (b - x) / (b - a);
135 return x;
138 a_float a_mf_s(a_float x, a_float a, a_float b)
140 if (x > (a + b) / 2)
142 if (x < b)
144 x = 1 - 2 * a_float_pow((b - x) / (b - a), 2);
146 else // x >= b
148 x = 1;
151 else // x <= (a+b)/2
153 if (x > a)
155 x = 2 * a_float_pow((x - a) / (b - a), 2);
157 else // x <= a
159 x = 0;
162 return x;
165 a_float a_mf_z(a_float x, a_float a, a_float b)
167 if (x < (a + b) / 2)
169 if (x > a)
171 x = 1 - 2 * a_float_pow((x - a) / (b - a), 2);
173 else // x <= a
175 x = 1;
178 else // x >= (a+b)/2
180 if (x < b)
182 x = 2 * a_float_pow((b - x) / (b - a), 2);
184 else // x >= b
186 x = 0;
189 return x;
192 a_float a_mf_pi(a_float x, a_float a, a_float b, a_float c, a_float d)
194 if (x < b)
196 x = a_mf_s(x, a, b);
198 else if (x > c)
200 x = a_mf_z(x, c, d);
202 else
204 x = 1;
206 return x;
209 a_float a_mf(unsigned int e, a_float x, a_float const *a)
211 switch (e)
213 case A_MF_PI:
214 return a_mf_pi(x, a[0], a[1], a[2], a[3]);
215 case A_MF_Z:
216 return a_mf_z(x, a[0], a[1]);
217 case A_MF_S:
218 return a_mf_s(x, a[0], a[1]);
219 case A_MF_LINZ:
220 return a_mf_linz(x, a[0], a[1]);
221 case A_MF_LINS:
222 return a_mf_lins(x, a[0], a[1]);
223 case A_MF_TRI:
224 return a_mf_tri(x, a[0], a[1], a[2]);
225 case A_MF_TRAP:
226 return a_mf_trap(x, a[0], a[1], a[2], a[3]);
227 case A_MF_PSIG:
228 return a_mf_psig(x, a[0], a[1], a[2], a[3]);
229 case A_MF_DSIG:
230 return a_mf_dsig(x, a[0], a[1], a[2], a[3]);
231 case A_MF_SIG:
232 return a_mf_sig(x, a[0], a[1]);
233 case A_MF_GBELL:
234 return a_mf_gbell(x, a[0], a[1], a[2]);
235 case A_MF_GAUSS2:
236 return a_mf_gauss2(x, a[0], a[1], a[2], a[3]);
237 case A_MF_GAUSS:
238 return a_mf_gauss(x, a[0], a[1]);
239 case A_MF_NUL:
240 default:
241 return 0;