1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 package org.hipparchus.analysis.polynomials;
23
24 import org.hipparchus.CalculusFieldElement;
25 import org.hipparchus.analysis.differentiation.*;
26 import org.hipparchus.complex.Complex;
27 import org.hipparchus.exception.MathIllegalArgumentException;
28 import org.hipparchus.random.RandomDataGenerator;
29 import org.hipparchus.util.Binary64;
30 import org.hipparchus.util.FastMath;
31 import org.junit.Assert;
32 import org.junit.Test;
33
34
35
36
37
38 public final class FieldPolynomialFunctionTest {
39
40 protected double tolerance = 1e-12;
41
42
43
44
45
46
47 @Test
48 public void testConstants() {
49 double c0 = 2.5;
50 FieldPolynomialFunction<Binary64> f = buildD64(c0);
51
52
53 Assert.assertEquals(c0, f.value(0).getReal(), tolerance);
54 Assert.assertEquals(c0, f.value(-1).getReal(), tolerance);
55 Assert.assertEquals(c0, f.value(-123.5).getReal(), tolerance);
56 Assert.assertEquals(c0, f.value(3).getReal(), tolerance);
57 Assert.assertEquals(c0, f.value(new Binary64(456.89)).getReal(), tolerance);
58
59 Assert.assertEquals(0, f.degree());
60 Assert.assertEquals(0, f.polynomialDerivative().value(0).getReal(), tolerance);
61
62 Assert.assertEquals(0, f.polynomialDerivative().polynomialDerivative().value(0).getReal(), tolerance);
63 }
64
65
66
67
68
69
70
71
72
73
74 @Test
75 public void testLinear() {
76 FieldPolynomialFunction<Binary64> f = buildD64(-1.5, 3);
77
78
79 Assert.assertEquals(-1.5, f.value(new Binary64(0)).getReal(), tolerance);
80
81
82 Assert.assertEquals(-4.5, f.value(new Binary64(-1)).getReal(), tolerance);
83 Assert.assertEquals(-9, f.value(new Binary64(-2.5)).getReal(), tolerance);
84 Assert.assertEquals(0, f.value(new Binary64(0.5)).getReal(), tolerance);
85 Assert.assertEquals(3, f.value(new Binary64(1.5)).getReal(), tolerance);
86 Assert.assertEquals(7.5, f.value(new Binary64(3)).getReal(), tolerance);
87
88 Assert.assertEquals(1, f.degree());
89
90 Assert.assertEquals(0, f.polynomialDerivative().polynomialDerivative().value(0).getReal(), tolerance);
91 }
92
93
94
95
96
97 @Test
98 public void testQuadratic() {
99 FieldPolynomialFunction<Binary64> f = buildD64(-2, -3, 2);
100
101
102 Assert.assertEquals(-2, f.value(0).getReal(), tolerance);
103
104
105 Assert.assertEquals(0, f.value(-0.5).getReal(), tolerance);
106 Assert.assertEquals(0, f.value(2).getReal(), tolerance);
107 Assert.assertEquals(-2, f.value(1.5).getReal(), tolerance);
108 Assert.assertEquals(7, f.value(-1.5).getReal(), tolerance);
109 Assert.assertEquals(265.5312, f.value(12.34).getReal(), tolerance);
110 }
111
112
113
114
115
116 @Test
117 public void testQuintic() {
118 FieldPolynomialFunction<Binary64> f = buildD64(0, 0, 15, -13, -3, 1);
119
120
121 Assert.assertEquals(0, f.value(0).getReal(), tolerance);
122
123
124 Assert.assertEquals(0, f.value(5).getReal(), tolerance);
125 Assert.assertEquals(0, f.value(1).getReal(), tolerance);
126 Assert.assertEquals(0, f.value(-3).getReal(), tolerance);
127 Assert.assertEquals(54.84375, f.value(-1.5).getReal(), tolerance);
128 Assert.assertEquals(-8.06637, f.value(1.3).getReal(), tolerance);
129
130 Assert.assertEquals(5, f.degree());
131 }
132
133
134
135
136
137
138
139
140 @Test
141 public void testfirstDerivativeComparison() {
142 double[] f_coeff = { 3, 6, -2, 1 };
143 double[] g_coeff = { 6, -4, 3 };
144 double[] h_coeff = { -4, 6 };
145
146 FieldPolynomialFunction<Binary64> f = buildD64(f_coeff);
147 FieldPolynomialFunction<Binary64> g = buildD64(g_coeff);
148 FieldPolynomialFunction<Binary64> h = buildD64(h_coeff);
149
150
151 Assert.assertEquals(f.polynomialDerivative().value(0).getReal(), g.value(0).getReal(), tolerance);
152 Assert.assertEquals(f.polynomialDerivative().value(1).getReal(), g.value(1).getReal(), tolerance);
153 Assert.assertEquals(f.polynomialDerivative().value(100).getReal(), g.value(100).getReal(), tolerance);
154 Assert.assertEquals(f.polynomialDerivative().value(4.1).getReal(), g.value(4.1).getReal(), tolerance);
155 Assert.assertEquals(f.polynomialDerivative().value(-3.25).getReal(), g.value(-3.25).getReal(), tolerance);
156
157
158 Assert.assertEquals(g.polynomialDerivative().value(FastMath.PI).getReal(), h.value(FastMath.PI).getReal(), tolerance);
159 Assert.assertEquals(g.polynomialDerivative().value(FastMath.E).getReal(), h.value(FastMath.E).getReal(), tolerance);
160 }
161
162 @Test
163 public void testAddition() {
164 FieldPolynomialFunction<Binary64> p1 = buildD64( -2, 1 );
165 FieldPolynomialFunction<Binary64> p2 = buildD64( 2, -1, 0 );
166 checkNullPolynomial(p1.add(p2));
167
168 p2 = p1.add(p1);
169 checkCoeffs(Double.MIN_VALUE, p2, -4, 2);
170
171 p1 = buildD64( 1, -4, 2 );
172 p2 = buildD64( -1, 3, -2 );
173 p1 = p1.add(p2);
174 Assert.assertEquals(1, p1.degree());
175 checkCoeffs(Double.MIN_VALUE, p1, 0, -1);
176 }
177
178 @Test
179 public void testSubtraction() {
180 FieldPolynomialFunction<Binary64> p1 = buildD64( -2, 1 );
181 checkNullPolynomial(p1.subtract(p1));
182
183 FieldPolynomialFunction<Binary64> p2 = buildD64( -2, 6 );
184 p2 = p2.subtract(p1);
185 checkCoeffs(Double.MIN_VALUE, p2, 0, 5);
186
187 p1 = buildD64( 1, -4, 2 );
188 p2 = buildD64( -1, 3, 2 );
189 p1 = p1.subtract(p2);
190 Assert.assertEquals(1, p1.degree());
191 checkCoeffs(Double.MIN_VALUE, p1, 2, -7);
192 }
193
194 @Test
195 public void testMultiplication() {
196 FieldPolynomialFunction<Binary64> p1 = buildD64( -3, 2 );
197 FieldPolynomialFunction<Binary64> p2 = buildD64( 3, 2, 1 );
198 checkCoeffs(Double.MIN_VALUE, p1.multiply(p2), -9, 0, 1, 2);
199
200 p1 = buildD64( 0, 1 );
201 p2 = p1;
202 for (int i = 2; i < 10; ++i) {
203 p2 = p2.multiply(p1);
204 double[] c = new double[i + 1];
205 c[i] = 1;
206 checkCoeffs(Double.MIN_VALUE, p2, c);
207 }
208 }
209
210
211
212
213
214
215
216
217 @Test
218 public void testMath341() {
219 double[] f_coeff = { 3, 6, -2, 1 };
220 double[] g_coeff = { 6, -4, 3 };
221 double[] h_coeff = { -4, 6 };
222
223 FieldPolynomialFunction<Binary64> f = buildD64(f_coeff);
224 FieldPolynomialFunction<Binary64> g = buildD64(g_coeff);
225 FieldPolynomialFunction<Binary64> h = buildD64(h_coeff);
226
227
228 Assert.assertEquals(f.polynomialDerivative().value(0).getReal(), g.value(0).getReal(), tolerance);
229 Assert.assertEquals(f.polynomialDerivative().value(1).getReal(), g.value(1).getReal(), tolerance);
230 Assert.assertEquals(f.polynomialDerivative().value(100).getReal(), g.value(100).getReal(), tolerance);
231 Assert.assertEquals(f.polynomialDerivative().value(4.1).getReal(), g.value(4.1).getReal(), tolerance);
232 Assert.assertEquals(f.polynomialDerivative().value(-3.25).getReal(), g.value(-3.25).getReal(), tolerance);
233
234
235 Assert.assertEquals(g.polynomialDerivative().value(FastMath.PI).getReal(), h.value(FastMath.PI).getReal(), tolerance);
236 Assert.assertEquals(g.polynomialDerivative().value(FastMath.E).getReal(), h.value(FastMath.E).getReal(), tolerance);
237 }
238
239 @Test
240 public void testAntiDerivative() {
241
242 final double[] coeff = {1, 2, 3};
243 final FieldPolynomialFunction<Binary64> p = buildD64(coeff);
244
245 checkCoeffs(Double.MIN_VALUE, p.antiDerivative(), 0, 1, 1, 1);
246 }
247
248 @Test
249 public void testAntiDerivativeConstant() {
250 final double[] coeff = {2};
251 final FieldPolynomialFunction<Binary64> p = buildD64(coeff);
252 checkCoeffs(Double.MIN_VALUE, p.antiDerivative(), 0, 2);
253 }
254
255 @Test
256 public void testAntiDerivativeZero() {
257 final double[] coeff = {0};
258 final FieldPolynomialFunction<Binary64> p = buildD64(coeff);
259 checkCoeffs(Double.MIN_VALUE, p.antiDerivative(), 0);
260 }
261
262 @Test
263 public void testAntiDerivativeRandom() {
264 final RandomDataGenerator ran = new RandomDataGenerator(1000);
265 double[] coeff = null;
266 FieldPolynomialFunction<Binary64> p = null;
267 int d = 0;
268 for (int i = 0; i < 20; i++) {
269 d = ran.nextInt(1, 50);
270 coeff = new double[d];
271 for (int j = 0; j < d; j++) {
272 coeff[j] = ran.nextUniform(-100, 1000);
273 }
274 p = buildD64(coeff);
275 checkInverseDifferentiation(p);
276 }
277 }
278
279 @Test
280 public void testIntegrate() {
281
282 final double[] coeff = {0, 0, -1};
283 final FieldPolynomialFunction<Binary64> p = buildD64(coeff);
284 Assert.assertEquals(-2d/3d, p.integrate(-1, 1).getReal(),Double.MIN_VALUE);
285
286
287 final FieldPolynomialFunction<Binary64> p2 = buildD64(0, 1).
288 multiply(buildD64(-1, 1)).
289 multiply(buildD64(1, 1));
290 Assert.assertEquals(0, p2.integrate(-1, 1).getReal(), Double.MIN_VALUE);
291 }
292
293 @Test(expected = MathIllegalArgumentException.class)
294 public void testIntegrateInfiniteBounds() {
295 final FieldPolynomialFunction<Binary64> p = buildD64(1);
296 p.integrate(0, Double.POSITIVE_INFINITY);
297 }
298
299 @Test(expected = MathIllegalArgumentException.class)
300 public void testIntegrateBadInterval() {
301 final FieldPolynomialFunction<Binary64> p = buildD64(1);
302 p.integrate(0, -1);
303 }
304
305 @Test
306 public void testIssue259WithComplex() {
307 final double nonZeroParameterForQuadraticCoeff = -1.;
308 final Complex[] coefficients = buildImaginaryCoefficients(1., 2., nonZeroParameterForQuadraticCoeff);
309 templateIssue259DisappearingCoefficients(coefficients);
310 }
311
312 @Test
313 public void testIssue259WithGradient() {
314 final double nonZeroParameterForQuadraticCoeff = -1.;
315 final Gradient[] coefficients = buildUnivariateGradientCoefficients(1.,2., nonZeroParameterForQuadraticCoeff);
316 templateIssue259DisappearingCoefficients(coefficients);
317 }
318
319 @Test
320 public void testIssue259WithDerivativeStructure() {
321 final double nonZeroParameterForQuadraticCoeff = -1.;
322 final DerivativeStructure[] coefficients = buildUnivariateDSCoefficients(1.,2., nonZeroParameterForQuadraticCoeff);
323 templateIssue259DisappearingCoefficients(coefficients);
324 }
325
326 @Test
327 public void testIssue259WithUnivariateDerivative1() {
328 final double nonZeroParameterForQuadraticCoeff = -1.;
329 final UnivariateDerivative1[] coefficients = buildUnivariateDerivative1Coefficients(1.,2., nonZeroParameterForQuadraticCoeff);
330 templateIssue259DisappearingCoefficients(coefficients);
331 }
332
333 @Test
334 public void testIssue259WithUnivariateDerivative2() {
335 final double nonZeroParameterForQuadraticCoeff = -1.;
336 final UnivariateDerivative2[] coefficients = buildUnivariateDerivative2Coefficients(1.,2., nonZeroParameterForQuadraticCoeff);
337 templateIssue259DisappearingCoefficients(coefficients);
338 }
339
340 private <T extends CalculusFieldElement<T>> void templateIssue259DisappearingCoefficients(T[] coefficients) {
341 final FieldPolynomialFunction<T> polynomialFunction = new FieldPolynomialFunction<>(coefficients);
342 Assert.assertEquals(coefficients.length, polynomialFunction.getCoefficients().length);
343 for (int i = 0; i < coefficients.length; i++) {
344 Assert.assertEquals(coefficients[i], polynomialFunction.getCoefficients()[i]);
345 }
346 }
347
348 private <T extends CalculusFieldElement<T>> void checkInverseDifferentiation(FieldPolynomialFunction<T> p) {
349 final T[] c0 = p.getCoefficients();
350 final T[] c1 = p.antiDerivative().polynomialDerivative().getCoefficients();
351 Assert.assertEquals(c0.length, c1.length);
352 for (int i = 0; i < c0.length; ++i) {
353 Assert.assertEquals(c0[i].getReal(), c1[i].getReal(), 1e-12);
354 }
355 }
356
357 private <T extends CalculusFieldElement<T>> void checkCoeffs(final double tolerance, final FieldPolynomialFunction<T> p,
358 final double... ref) {
359 final T[] c = p.getCoefficients();
360 Assert.assertEquals(ref.length, c.length);
361 for (int i = 0; i < ref.length; ++i) {
362 Assert.assertEquals(ref[i], c[i].getReal(), tolerance);
363 }
364 }
365
366 private <T extends CalculusFieldElement<T>> void checkNullPolynomial(FieldPolynomialFunction<T> p) {
367 for (T coefficient : p.getCoefficients()) {
368 Assert.assertEquals(0, coefficient.getReal(), 1e-15);
369 }
370 }
371
372 private FieldPolynomialFunction<Binary64> buildD64(double...c) {
373 Binary64[] array = new Binary64[c.length];
374 for (int i = 0; i < c.length; ++i) {
375 array[i] = new Binary64(c[i]);
376 }
377 return new FieldPolynomialFunction<>(array);
378 }
379
380 private Complex[] buildImaginaryCoefficients(double...c) {
381 Complex[] array = new Complex[c.length];
382 for (int i = 0; i < c.length; ++i) {
383 array[i] = new Complex(0., c[i]);
384 }
385 return array;
386 }
387
388 private DerivativeStructure[] buildUnivariateDSCoefficients(double...c) {
389 DerivativeStructure[] array = new DerivativeStructure[c.length];
390 final DSFactory factory = new DSFactory(1, 1);
391 for (int i = 0; i < c.length; ++i) {
392 array[i] = factory.variable(0, 0.).multiply(c[i]);
393 }
394 return array;
395 }
396
397 private Gradient[] buildUnivariateGradientCoefficients(double...c) {
398 Gradient[] array = new Gradient[c.length];
399 for (int i = 0; i < c.length; ++i) {
400 array[i] = Gradient.variable(1, 0, 0.).multiply(c[i]);
401 }
402 return array;
403 }
404
405 private UnivariateDerivative1[] buildUnivariateDerivative1Coefficients(double...c) {
406 UnivariateDerivative1[] array = new UnivariateDerivative1[c.length];
407 for (int i = 0; i < c.length; ++i) {
408 array[i] = new UnivariateDerivative1(0., c[i]);
409 }
410 return array;
411 }
412
413 private UnivariateDerivative2[] buildUnivariateDerivative2Coefficients(double...c) {
414 UnivariateDerivative2[] array = new UnivariateDerivative2[c.length];
415 for (int i = 0; i < c.length; ++i) {
416 array[i] = new UnivariateDerivative2(0., c[i], 0.);
417 }
418 return array;
419 }
420
421 }