View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *      http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  package org.apache.commons.math4.legacy.field.linalg;
18  
19  import org.junit.Assert;
20  import org.junit.Test;
21  import org.apache.commons.numbers.field.FP64;
22  import org.apache.commons.numbers.field.FP64Field;
23  import org.apache.commons.math4.legacy.core.Pair;
24  import org.apache.commons.math4.legacy.linear.RealMatrix;
25  import org.apache.commons.math4.legacy.linear.Array2DRowRealMatrix;
26  
27  /**
28   * Tests for {@link FieldDenseMatrix} (using {@link FP64} as field elements).
29   */
30  public class FP64FieldDenseMatrixTest {
31      @Test
32      public void testGetRowDimension() {
33          final int r = 6;
34          final int c = 9;
35          final FieldDenseMatrix<FP64> a = FieldDenseMatrix.create(FP64Field.get(), r, c);
36          Assert.assertEquals(r, a.getRowDimension());
37      }
38  
39      @Test
40      public void testGetColumnDimension() {
41          final int r = 6;
42          final int c = 9;
43          final FieldDenseMatrix<FP64> a = FieldDenseMatrix.create(FP64Field.get(), r, c);
44          Assert.assertEquals(c, a.getColumnDimension());
45      }
46  
47      @Test
48      public void testSetGet() {
49          final int r = 17;
50          final int c = 20;
51          final FieldDenseMatrix<FP64> a = FieldDenseMatrix.create(FP64Field.get(), r, c);
52  
53          int count = 0;
54          for (int i = 0; i < r; i++) {
55              for (int j = 0; j < c; j++) {
56                  a.set(i, j, FP64.of(count++));
57              }
58          }
59          Assert.assertEquals(r * c, count);
60  
61          count = 0;
62          for (int i = 0; i < r; i++) {
63              for (int j = 0; j < c; j++) {
64                  Assert.assertEquals((double) count++,
65                                      a.get(i, j).doubleValue(),
66                                      0d);
67              }
68          }
69      }
70  
71      @Test
72      public void testAdd() {
73          final int r = 5;
74          final int c = 3;
75          final double scale = 1e3;
76          final Pair<FieldDenseMatrix<FP64>, RealMatrix> p1 = createRandom(r, c, scale);
77          final Pair<FieldDenseMatrix<FP64>, RealMatrix> p2 = createRandom(r, c, scale);
78  
79          assertEquals(p1.getFirst().add(p2.getFirst()),
80                       p1.getSecond().add(p2.getSecond()),
81                       0d);
82      }
83  
84      @Test
85      public void testSubtract() {
86          final int r = 2;
87          final int c = 6;
88          final double scale = 1e3;
89          final Pair<FieldDenseMatrix<FP64>, RealMatrix> p1 = createRandom(r, c, scale);
90          final Pair<FieldDenseMatrix<FP64>, RealMatrix> p2 = createRandom(r, c, scale);
91  
92          assertEquals(p1.getFirst().subtract(p2.getFirst()),
93                       p1.getSecond().subtract(p2.getSecond()),
94                       0d);
95      }
96  
97      @Test
98      public void testMultiply() {
99          final int r = 7;
100         final int c1 = 4;
101         final int c2 = 5;
102         final double scale = 1e2;
103         final Pair<FieldDenseMatrix<FP64>, RealMatrix> p1 = createRandom(r, c1, scale);
104         final Pair<FieldDenseMatrix<FP64>, RealMatrix> p2 = createRandom(c1, c2, scale);
105 
106         assertEquals(p1.getFirst().multiply(p2.getFirst()),
107                      p1.getSecond().multiply(p2.getSecond()),
108                      0d);
109     }
110 
111     @Test
112     public void testNegate() {
113         final int dim = 13;
114         final double scale = 1;
115         final Pair<FieldDenseMatrix<FP64>, RealMatrix> p = createRandom(dim, dim, scale);
116 
117         assertEquals(p.getFirst().negate(),
118                      p.getSecond().scalarMultiply(-1),
119                      0d);
120     }
121 
122     @Test
123     public void testPowZero() {
124         final int dim = 5;
125         final double scale = 1e100;
126         final Pair<FieldDenseMatrix<FP64>, RealMatrix> p = createRandom(dim, dim, scale);
127 
128         final int exp = 0;
129         assertEquals(p.getFirst().pow(exp),
130                      p.getSecond().power(exp),
131                      0d);
132     }
133 
134     @Test
135     public void testPowOne() {
136         final int dim = 5;
137         final double scale = 1e100;
138         final Pair<FieldDenseMatrix<FP64>, RealMatrix> p = createRandom(dim, dim, scale);
139 
140         final int exp = 1;
141         assertEquals(p.getFirst().pow(exp),
142                      p.getSecond().power(exp),
143                      0d);
144     }
145 
146     @Test
147     public void testPow() {
148         final int dim = 5;
149         final double scale = 1e2;
150         final Pair<FieldDenseMatrix<FP64>, RealMatrix> p = createRandom(dim, dim, scale);
151 
152         final int exp = 4;
153         assertEquals(p.getFirst().pow(exp),
154                      p.getSecond().power(exp),
155                      0d);
156     }
157 
158     @Test
159     public void testGetField() {
160         final FieldDenseMatrix<FP64> a = FieldDenseMatrix.create(FP64Field.get(), 7, 5);
161         Assert.assertEquals(FP64Field.get(), a.getField());
162     }
163 
164     @Test
165     public void testEquals() {
166         // Reference equality.
167         final FieldDenseMatrix<FP64> a = FieldDenseMatrix.create(FP64Field.get(), 7, 2);
168         Assert.assertEquals(a, a);
169 
170         // Dimension mismatch
171         final FieldDenseMatrix<FP64> b = FieldDenseMatrix.create(FP64Field.get(), 7, 3);
172         Assert.assertNotEquals(a, b);
173         final FieldDenseMatrix<FP64> c = FieldDenseMatrix.create(FP64Field.get(), 6, 2);
174         Assert.assertNotEquals(a, c);
175 
176         // Contents.
177         final FieldDenseMatrix<FP64> d = FieldDenseMatrix.create(FP64Field.get(), 7, 2);
178         Assert.assertEquals(a, d); // Unitialized contents.
179         a.fill(FP64.of(1.23456789));
180         d.fill(FP64.of(1.23456789));
181         Assert.assertEquals(a, d); // Initialized contents.
182         d.set(6, 1, d.get(6, 1).add(FP64.of(1e-15)));
183         Assert.assertNotEquals(a, d);
184     }
185 
186     @Test
187     public void testCopy() {
188         final FieldDenseMatrix<FP64> a = FieldDenseMatrix.create(FP64Field.get(), 7, 3)
189             .fill(FP64Field.get().one());
190         final FieldDenseMatrix<FP64> b = a.copy();
191         Assert.assertEquals(a, b);
192 
193         b.set(0, 0, FP64Field.get().zero());
194         Assert.assertNotEquals(a, b);
195     }
196 
197     @Test
198     public void testTranspose() {
199         final int r = 4;
200         final int c = 5;
201         final FieldDenseMatrix<FP64> a = FieldDenseMatrix.create(FP64Field.get(), r, c);
202         for (int i = 0; i < r; i++) {
203             for (int j = 0; j < c; j++) {
204                 final double j2 = j * j;
205                 a.set(i, j,
206                       FP64.of(1.2 * i + 3.4 * j2));
207             }
208         }
209 
210         final FieldDenseMatrix<FP64> b = a.transpose();
211         for (int i = 0; i < r; i++) {
212             for (int j = 0; j < c; j++) {
213                 Assert.assertEquals(a.get(i, j), b.get(j, i));
214             }
215         }
216 
217         Assert.assertEquals(a, b.transpose());
218     }
219 
220     @Test
221     public void testIdentity() {
222         final int dim = 3;
223         final FieldDenseMatrix<FP64> a = FieldDenseMatrix.identity(FP64Field.get(), dim);
224         for (int i = 0; i < dim; i++) {
225             for (int j = 0; j < dim; j++) {
226                 if (i == j) {
227                     Assert.assertEquals(FP64Field.get().one(),                                        a.get(i, j));
228                 } else {
229                     Assert.assertEquals(FP64Field.get().zero(),
230                                         a.get(i, j));
231                 }
232             }
233         }
234     }
235 
236     /**
237      * Compares with result obtained from "Commons Math".
238      *
239      * @param a "o.a.c.m.field.linalg" result.
240      * @param b "o.a.c.m.linear" result.
241      * @param tol Tolerance.
242      */
243     private void assertEquals(FieldDenseMatrix<FP64> a,
244                               RealMatrix b,
245                               double tol) {
246         if (a.getRowDimension() != b.getRowDimension() ||
247             a.getColumnDimension() != b.getColumnDimension()) {
248             Assert.fail("Dimension mismatch");
249         }
250 
251         for (int i = 0; i < a.getRowDimension(); i++) {
252             for (int j = 0; j < a.getColumnDimension(); j++) {
253                 Assert.assertEquals("(" + i + ", " + j + ")",
254                                     a.get(i, j).doubleValue(),
255                                     b.getEntry(i, j),
256                                     tol);
257             }
258         }
259     }
260 
261     /**
262      * Creates test matrices with random entries.
263      *
264      * @param r Rows.
265      * @param c Columns.
266      * @param scale Range of the entries.
267      * @return a pair of matrices whose entries are in the interval
268      * {@code [-scale, scale]}.
269      */
270     private Pair<FieldDenseMatrix<FP64>, RealMatrix> createRandom(int r,
271                                                                   int c,
272                                                                   double scale) {
273         final FieldDenseMatrix<FP64> a = FieldDenseMatrix.create(FP64Field.get(), r, c);
274         final RealMatrix b = new Array2DRowRealMatrix(r, c);
275         for (int i = 0; i < r; i++) {
276             for (int j = 0; j < c; j++) {
277                 final double v = scale * (2 * Math.random() - 1);
278                 a.set(i, j, FP64.of(v));
279                 b.setEntry(i, j, v);
280             }
281         }
282 
283         return new Pair<>(a, b);
284     }
285 }