1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17 package org.hipparchus.analysis.integration.gauss;
18
19 import org.hipparchus.CalculusFieldElement;
20 import org.hipparchus.Field;
21 import org.hipparchus.exception.MathIllegalArgumentException;
22 import org.hipparchus.util.MathArrays;
23 import org.hipparchus.util.Pair;
24
25
26
27
28
29
30
31
32
33 public class FieldLaguerreRuleFactory<T extends CalculusFieldElement<T>> extends FieldAbstractRuleFactory<T> {
34
35
36
37
38 public FieldLaguerreRuleFactory(final Field<T> field) {
39 super(field);
40 }
41
42
43 @Override
44 public Pair<T[], T[]> computeRule(int numberOfPoints)
45 throws MathIllegalArgumentException {
46
47 final Field<T> field = getField();
48
49
50 final Laguerre<T> p = new Laguerre<>(numberOfPoints);
51 final T[] points = findRoots(numberOfPoints, p::ratio);
52
53
54 final T[] weights = MathArrays.buildArray(field, numberOfPoints);
55 final int n1 = numberOfPoints + 1;
56 final long n1Squared = n1 * (long) n1;
57 final Laguerre<T> laguerreN1 = new Laguerre<>(n1);
58 for (int i = 0; i < numberOfPoints; i++) {
59 final T y = laguerreN1.value(points[i]);
60 weights[i] = points[i].divide(y.square().multiply(n1Squared));
61 }
62
63 return new Pair<>(points, weights);
64
65 }
66
67
68
69
70 private static class Laguerre<T extends CalculusFieldElement<T>> {
71
72
73 private int degree;
74
75
76
77
78 Laguerre(int degree) {
79 this.degree = degree;
80 }
81
82
83
84
85
86 public T value(final T x) {
87 return lNlNm1(x)[0];
88 }
89
90
91
92
93
94 public T ratio(T x) {
95 T[] l = lNlNm1(x);
96 return x.multiply(l[0]).divide(l[0].subtract(l[1]).multiply(degree));
97 }
98
99
100
101
102
103 private T[] lNlNm1(final T x) {
104 T[] l = MathArrays.buildArray(x.getField(), 2);
105 l[0] = x.subtract(1).negate();
106 l[1] = x.getField().getOne();
107 for (int n = 1; n < degree; n++) {
108
109 final T lp = l[0].multiply(x.negate().add(2 * n + 1)).subtract(l[1].multiply(n)).divide(n + 1);
110 l[1] = l[0];
111 l[0] = lp;
112 }
113 return l;
114 }
115
116 }
117
118 }