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.fitting.leastsquares;
18  
19  import org.apache.commons.math4.legacy.fitting.leastsquares.LeastSquaresProblem.Evaluation;
20  import org.apache.commons.math4.legacy.linear.ArrayRealVector;
21  import org.apache.commons.math4.legacy.linear.DecompositionSolver;
22  import org.apache.commons.math4.legacy.linear.QRDecomposition;
23  import org.apache.commons.math4.legacy.linear.RealMatrix;
24  import org.apache.commons.math4.legacy.linear.RealVector;
25  import org.apache.commons.math4.core.jdkmath.JdkMath;
26  
27  /**
28   * An implementation of {@link Evaluation} that is designed for extension. All of the
29   * methods implemented here use the methods that are left unimplemented.
30   * <p>
31   * TODO cache results?
32   *
33   * @since 3.3
34   */
35  public abstract class AbstractEvaluation implements Evaluation {
36  
37      /** number of observations. */
38      private final int observationSize;
39  
40      /**
41       * Constructor.
42       *
43       * @param observationSize the number of observations.
44       * Needed for {@link #getRMS()} and {@link #getReducedChiSquare(int)}.
45       */
46      AbstractEvaluation(final int observationSize) {
47          this.observationSize = observationSize;
48      }
49  
50      /** {@inheritDoc} */
51      @Override
52      public RealMatrix getCovariances(double threshold) {
53          // Set up the Jacobian.
54          final RealMatrix j = this.getJacobian();
55  
56          // Compute transpose(J)J.
57          final RealMatrix jTj = j.transpose().multiply(j);
58  
59          // Compute the covariances matrix.
60          final DecompositionSolver solver
61                  = new QRDecomposition(jTj, threshold).getSolver();
62          return solver.getInverse();
63      }
64  
65      /** {@inheritDoc} */
66      @Override
67      public RealVector getSigma(double covarianceSingularityThreshold) {
68          final RealMatrix cov = this.getCovariances(covarianceSingularityThreshold);
69          final int nC = cov.getColumnDimension();
70          final RealVector sig = new ArrayRealVector(nC);
71          for (int i = 0; i < nC; ++i) {
72              sig.setEntry(i, JdkMath.sqrt(cov.getEntry(i,i)));
73          }
74          return sig;
75      }
76  
77      /** {@inheritDoc} */
78      @Override
79      public double getRMS() {
80          return JdkMath.sqrt(getReducedChiSquare(1));
81      }
82  
83      /** {@inheritDoc} */
84      @Override
85      public double getCost() {
86          return JdkMath.sqrt(getChiSquare());
87      }
88  
89      /** {@inheritDoc} */
90      @Override
91      public double getChiSquare() {
92          final ArrayRealVector r = new ArrayRealVector(getResiduals());
93          return r.dotProduct(r);
94      }
95  
96      /** {@inheritDoc} */
97      @Override
98      public double getReducedChiSquare(int numberOfFittedParameters) {
99          return getChiSquare() / (observationSize - numberOfFittedParameters + 1);
100     }
101 }