CMS 3D CMS Logo

sicif.h
Go to the documentation of this file.
1 /* sicif.c
2  *
3  * Sine and cosine integrals
4  *
5  *
6  *
7  * SYNOPSIS:
8  *
9  * float x, Ci, Si;
10  *
11  * sicif( x, &Si, &Ci );
12  *
13  *
14  * DESCRIPTION:
15  *
16  * Evaluates the integrals
17  *
18  * x
19  * -
20  * | cos t - 1
21  * Ci(x) = eul + ln x + | --------- dt,
22  * | t
23  * -
24  * 0
25  * x
26  * -
27  * | sin t
28  * Si(x) = | ----- dt
29  * | t
30  * -
31  * 0
32  *
33  * where eul = 0.57721566490153286061 is Euler's constant.
34  * The integrals are approximated by rational functions.
35  * For x > 8 auxiliary functions f(x) and g(x) are employed
36  * such that
37  *
38  * Ci(x) = f(x) sin(x) - g(x) cos(x)
39  * Si(x) = pi/2 - f(x) cos(x) - g(x) sin(x)
40  *
41  *
42  * ACCURACY:
43  * Test interval = [0,50].
44  * Absolute error, except relative when > 1:
45  * arithmetic function # trials peak rms
46  * IEEE Si 30000 2.1e-7 4.3e-8
47  * IEEE Ci 30000 3.9e-7 2.2e-8
48  */
49 
50 /*
51  Cephes Math Library Release 2.1: January, 1989
52  Copyright 1984, 1987, 1989 by Stephen L. Moshier
53  Direct inquiries to 30 Frost Street, Cambridge, MA 02140
54  */
55 
56 #include "vdt/vdtMath.h"
57 
58 static const float SN[] = {
59  -8.39167827910303881427E-11,
60  4.62591714427012837309E-8,
61  -9.75759303843632795789E-6,
62  9.76945438170435310816E-4,
63  -4.13470316229406538752E-2,
64  1.00000000000000000302E0,
65 };
66 static const float SD[] = {
67  2.03269266195951942049E-12,
68  1.27997891179943299903E-9,
69  4.41827842801218905784E-7,
70  9.96412122043875552487E-5,
71  1.42085239326149893930E-2,
72  9.99999999999999996984E-1,
73 };
74 
75 static const float CN[] = {
76  2.02524002389102268789E-11,
77  -1.35249504915790756375E-8,
78  3.59325051419993077021E-6,
79  -4.74007206873407909465E-4,
80  2.89159652607555242092E-2,
81  -1.00000000000000000080E0,
82 };
83 static const float CD[] = {
84  4.07746040061880559506E-12,
85  3.06780997581887812692E-9,
86  1.23210355685883423679E-6,
87  3.17442024775032769882E-4,
88  5.10028056236446052392E-2,
89  4.00000000000000000080E0,
90 };
91 
92 static const float FN4[] = {
93  4.23612862892216586994E0,
94  5.45937717161812843388E0,
95  1.62083287701538329132E0,
96  1.67006611831323023771E-1,
97  6.81020132472518137426E-3,
98  1.08936580650328664411E-4,
99  5.48900223421373614008E-7,
100 };
101 static const float FD4[] = {
102  /* 1.00000000000000000000E0,*/
103  8.16496634205391016773E0,
104  7.30828822505564552187E0,
105  1.86792257950184183883E0,
106  1.78792052963149907262E-1,
107  7.01710668322789753610E-3,
108  1.10034357153915731354E-4,
109  5.48900252756255700982E-7,
110 };
111 
112 static const float FN8[] = {
113  4.55880873470465315206E-1,
114  7.13715274100146711374E-1,
115  1.60300158222319456320E-1,
116  1.16064229408124407915E-2,
117  3.49556442447859055605E-4,
118  4.86215430826454749482E-6,
119  3.20092790091004902806E-8,
120  9.41779576128512936592E-11,
121  9.70507110881952024631E-14,
122 };
123 static const float FD8[] = {
124  /* 1.00000000000000000000E0,*/
125  9.17463611873684053703E-1,
126  1.78685545332074536321E-1,
127  1.22253594771971293032E-2,
128  3.58696481881851580297E-4,
129  4.92435064317881464393E-6,
130  3.21956939101046018377E-8,
131  9.43720590350276732376E-11,
132  9.70507110881952025725E-14,
133 };
134 
135 static const float GN4[] = {
136  8.71001698973114191777E-2,
137  6.11379109952219284151E-1,
138  3.97180296392337498885E-1,
139  7.48527737628469092119E-2,
140  5.38868681462177273157E-3,
141  1.61999794598934024525E-4,
142  1.97963874140963632189E-6,
143  7.82579040744090311069E-9,
144 };
145 static const float GD4[] = {
146  /* 1.00000000000000000000E0,*/
147  1.64402202413355338886E0,
148  6.66296701268987968381E-1,
149  9.88771761277688796203E-2,
150  6.22396345441768420760E-3,
151  1.73221081474177119497E-4,
152  2.02659182086343991969E-6,
153  7.82579218933534490868E-9,
154 };
155 
156 static const float GN8[] = {
157  6.97359953443276214934E-1,
158  3.30410979305632063225E-1,
159  3.84878767649974295920E-2,
160  1.71718239052347903558E-3,
161  3.48941165502279436777E-5,
162  3.47131167084116673800E-7,
163  1.70404452782044526189E-9,
164  3.85945925430276600453E-12,
165  3.14040098946363334640E-15,
166 };
167 static const float GD8[] = {
168  /* 1.00000000000000000000E0,*/
169  1.68548898811011640017E0,
170  4.87852258695304967486E-1,
171  4.67913194259625806320E-2,
172  1.90284426674399523638E-3,
173  3.68475504442561108162E-5,
174  3.57043223443740838771E-7,
175  1.72693748966316146736E-9,
176  3.87830166023954706752E-12,
177  3.14040098946363335242E-15,
178 };
179 
180 inline float polevlf(float xx, const float *coef, int N) {
181  float ans, x;
182  const float *p;
183  int i;
184 
185  x = xx;
186  p = coef;
187  ans = *p++;
188 
189  i = N;
190  do
191  ans = ans * x + *p++;
192  while (--i);
193 
194  return (ans);
195 }
196 
197 /* p1evl() */
198 /* N
199  * Evaluate polynomial when coefficient of x is 1.0.
200  * Otherwise same as polevl.
201  */
202 inline float p1evlf(float xx, const float *coef, int N) {
203  float ans, x;
204  const float *p;
205  int i;
206 
207  x = xx;
208  p = coef;
209  ans = x + *p++;
210  i = N - 1;
211 
212  do
213  ans = ans * x + *p++;
214  while (--i);
215 
216  return (ans);
217 }
218 
219 inline int sicif(float xx, float &si, float &ci) {
220  const float MAXNUMF = 1.7014117331926442990585209174225846272e38;
221  const float PIO2F = 1.5707963267948966192;
222  // const float MACHEPF = 5.9604644775390625E-8;
223  const float EUL = 0.57721566490153286061;
224 
225  float x, z, c, s, f, g;
226  int sign;
227 
228  x = xx;
229  if (x < 0.0f) {
230  sign = -1;
231  x = -x;
232  } else
233  sign = 0;
234 
235  if (x == 0.0f) {
236  si = 0.0;
237  ci = -MAXNUMF;
238  return (0);
239  }
240 
241  if (x > 1.0e9f) {
242  float su, cu;
243  vdt::fast_sincosf(x, su, cu);
244  si = PIO2F - cu / x;
245  ci = su / x;
246  return (0);
247  }
248 
249  if (x > 4.0f)
250  goto asympt;
251 
252  z = x * x;
253  s = x * polevlf(z, SN, 5) / polevlf(z, SD, 5);
254  c = z * polevlf(z, CN, 5) / polevlf(z, CD, 5);
255 
256  if (sign)
257  s = -s;
258  si = s;
259  ci = EUL + vdt::fast_logf(x) + c; /* real part if x < 0 */
260  return (0);
261 
262  /* The auxiliary functions are:
263  *
264  *
265  * *si = *si - PIO2;
266  * c = cos(x);
267  * s = sin(x);
268  *
269  * t = *ci * s - *si * c;
270  * a = *ci * c + *si * s;
271  *
272  * *si = t;
273  * *ci = -a;
274  */
275 
276 asympt:
277  vdt::fast_sincosf(x, s, c);
278  z = 1.0f / (x * x);
279  if (x < 8.0f) {
280  f = polevlf(z, FN4, 6) / (x * p1evlf(z, FD4, 7));
281  g = z * polevlf(z, GN4, 7) / p1evlf(z, GD4, 7);
282  } else {
283  f = polevlf(z, FN8, 8) / (x * p1evlf(z, FD8, 8));
284  g = z * polevlf(z, GN8, 8) / p1evlf(z, GD8, 9);
285  }
286  si = PIO2F - f * c - g * s;
287  if (sign)
288  si = -(si);
289  ci = f * s - g * c;
290 
291  return (0);
292 }
static const float FN8[]
Definition: sicif.h:112
The Signals That Services Can Subscribe To This is based on ActivityRegistry and is current per Services can connect to the signals distributed by the ActivityRegistry in order to monitor the activity of the application Each possible callback has some defined which we here list in angle e g
Definition: Activities.doc:4
float float float z
static const float GD8[]
Definition: sicif.h:167
static const float SN[]
Definition: sicif.h:58
static const float SD[]
Definition: sicif.h:66
static const float FN4[]
Definition: sicif.h:92
float polevlf(float xx, const float *coef, int N)
Definition: sicif.h:180
double f[11][100]
static const float CD[]
Definition: sicif.h:83
static const float GD4[]
Definition: sicif.h:145
#define N
Definition: blowfish.cc:9
static const float GN8[]
Definition: sicif.h:156
static const float CN[]
Definition: sicif.h:75
static const float FD4[]
Definition: sicif.h:101
static const float GN4[]
Definition: sicif.h:135
float fast_logf(float x)
float p1evlf(float xx, const float *coef, int N)
Definition: sicif.h:202
static const float FD8[]
Definition: sicif.h:123
int sicif(float xx, float &si, float &ci)
Definition: sicif.h:219