summaryrefslogtreecommitdiff
path: root/src/main/java/org/apache/commons/math/analysis/solvers/UnivariateRealSolverImpl.java
diff options
context:
space:
mode:
Diffstat (limited to 'src/main/java/org/apache/commons/math/analysis/solvers/UnivariateRealSolverImpl.java')
-rw-r--r--src/main/java/org/apache/commons/math/analysis/solvers/UnivariateRealSolverImpl.java304
1 files changed, 304 insertions, 0 deletions
diff --git a/src/main/java/org/apache/commons/math/analysis/solvers/UnivariateRealSolverImpl.java b/src/main/java/org/apache/commons/math/analysis/solvers/UnivariateRealSolverImpl.java
new file mode 100644
index 0000000..557c767
--- /dev/null
+++ b/src/main/java/org/apache/commons/math/analysis/solvers/UnivariateRealSolverImpl.java
@@ -0,0 +1,304 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package org.apache.commons.math.analysis.solvers;
+
+import org.apache.commons.math.ConvergingAlgorithmImpl;
+import org.apache.commons.math.FunctionEvaluationException;
+import org.apache.commons.math.MathRuntimeException;
+import org.apache.commons.math.analysis.UnivariateRealFunction;
+import org.apache.commons.math.exception.util.LocalizedFormats;
+import org.apache.commons.math.ConvergenceException;
+import org.apache.commons.math.exception.NullArgumentException;
+
+/**
+ * Provide a default implementation for several functions useful to generic
+ * solvers.
+ *
+ * @version $Revision: 1070725 $ $Date: 2011-02-15 02:31:12 +0100 (mar. 15 févr. 2011) $
+ * @deprecated in 2.2 (to be removed in 3.0).
+ */
+@Deprecated
+public abstract class UnivariateRealSolverImpl
+ extends ConvergingAlgorithmImpl implements UnivariateRealSolver {
+
+ /** Maximum error of function. */
+ protected double functionValueAccuracy;
+
+ /** Default maximum error of function. */
+ protected double defaultFunctionValueAccuracy;
+
+ /** Indicates where a root has been computed. */
+ protected boolean resultComputed = false;
+
+ /** The last computed root. */
+ protected double result;
+
+ /** Value of the function at the last computed result. */
+ protected double functionValue;
+
+ /** The function to solve.
+ * @deprecated as of 2.0 the function to solve is passed as an argument
+ * to the {@link #solve(UnivariateRealFunction, double, double)} or
+ * {@link UnivariateRealSolverImpl#solve(UnivariateRealFunction, double, double, double)}
+ * method. */
+ @Deprecated
+ protected UnivariateRealFunction f;
+
+ /**
+ * Construct a solver with given iteration count and accuracy.
+ *
+ * @param f the function to solve.
+ * @param defaultAbsoluteAccuracy maximum absolute error
+ * @param defaultMaximalIterationCount maximum number of iterations
+ * @throws IllegalArgumentException if f is null or the
+ * defaultAbsoluteAccuracy is not valid
+ * @deprecated as of 2.0 the function to solve is passed as an argument
+ * to the {@link #solve(UnivariateRealFunction, double, double)} or
+ * {@link UnivariateRealSolverImpl#solve(UnivariateRealFunction, double, double, double)}
+ * method.
+ */
+ @Deprecated
+ protected UnivariateRealSolverImpl(final UnivariateRealFunction f,
+ final int defaultMaximalIterationCount,
+ final double defaultAbsoluteAccuracy) {
+ super(defaultMaximalIterationCount, defaultAbsoluteAccuracy);
+ if (f == null) {
+ throw new NullArgumentException(LocalizedFormats.FUNCTION);
+ }
+ this.f = f;
+ this.defaultFunctionValueAccuracy = 1.0e-15;
+ this.functionValueAccuracy = defaultFunctionValueAccuracy;
+ }
+
+ /**
+ * Construct a solver with given iteration count and accuracy.
+ *
+ * @param defaultAbsoluteAccuracy maximum absolute error
+ * @param defaultMaximalIterationCount maximum number of iterations
+ * @throws IllegalArgumentException if f is null or the
+ * defaultAbsoluteAccuracy is not valid
+ */
+ protected UnivariateRealSolverImpl(final int defaultMaximalIterationCount,
+ final double defaultAbsoluteAccuracy) {
+ super(defaultMaximalIterationCount, defaultAbsoluteAccuracy);
+ this.defaultFunctionValueAccuracy = 1.0e-15;
+ this.functionValueAccuracy = defaultFunctionValueAccuracy;
+ }
+
+ /** Check if a result has been computed.
+ * @exception IllegalStateException if no result has been computed
+ */
+ protected void checkResultComputed() throws IllegalStateException {
+ if (!resultComputed) {
+ throw MathRuntimeException.createIllegalStateException(LocalizedFormats.NO_RESULT_AVAILABLE);
+ }
+ }
+
+ /** {@inheritDoc} */
+ public double getResult() {
+ checkResultComputed();
+ return result;
+ }
+
+ /** {@inheritDoc} */
+ public double getFunctionValue() {
+ checkResultComputed();
+ return functionValue;
+ }
+
+ /** {@inheritDoc} */
+ public void setFunctionValueAccuracy(final double accuracy) {
+ functionValueAccuracy = accuracy;
+ }
+
+ /** {@inheritDoc} */
+ public double getFunctionValueAccuracy() {
+ return functionValueAccuracy;
+ }
+
+ /** {@inheritDoc} */
+ public void resetFunctionValueAccuracy() {
+ functionValueAccuracy = defaultFunctionValueAccuracy;
+ }
+
+ /**
+ * Solve for a zero root in the given interval.
+ * <p>A solver may require that the interval brackets a single zero root.
+ * Solvers that do require bracketing should be able to handle the case
+ * where one of the endpoints is itself a root.</p>
+ *
+ * @param function the function to solve.
+ * @param min the lower bound for the interval.
+ * @param max the upper bound for the interval.
+ * @param maxEval Maximum number of evaluations.
+ * @return a value where the function is zero
+ * @throws ConvergenceException if the maximum iteration count is exceeded
+ * or the solver detects convergence problems otherwise.
+ * @throws FunctionEvaluationException if an error occurs evaluating the function
+ * @throws IllegalArgumentException if min > max or the endpoints do not
+ * satisfy the requirements specified by the solver
+ * @since 2.2
+ */
+ public double solve(int maxEval, UnivariateRealFunction function, double min, double max)
+ throws ConvergenceException, FunctionEvaluationException {
+ throw MathRuntimeException.createUnsupportedOperationException(LocalizedFormats.NOT_OVERRIDEN);
+ }
+
+ /**
+ * Solve for a zero in the given interval, start at startValue.
+ * <p>A solver may require that the interval brackets a single zero root.
+ * Solvers that do require bracketing should be able to handle the case
+ * where one of the endpoints is itself a root.</p>
+ *
+ * @param function the function to solve.
+ * @param min the lower bound for the interval.
+ * @param max the upper bound for the interval.
+ * @param startValue the start value to use
+ * @param maxEval Maximum number of evaluations.
+ * @return a value where the function is zero
+ * @throws ConvergenceException if the maximum iteration count is exceeded
+ * or the solver detects convergence problems otherwise.
+ * @throws FunctionEvaluationException if an error occurs evaluating the function
+ * @throws IllegalArgumentException if min > max or the arguments do not
+ * satisfy the requirements specified by the solver
+ * @since 2.2
+ */
+ public double solve(int maxEval, UnivariateRealFunction function, double min, double max, double startValue)
+ throws ConvergenceException, FunctionEvaluationException, IllegalArgumentException {
+ throw MathRuntimeException.createUnsupportedOperationException(LocalizedFormats.NOT_OVERRIDEN);
+ }
+
+ /**
+ * Convenience function for implementations.
+ *
+ * @param newResult the result to set
+ * @param iterationCount the iteration count to set
+ */
+ protected final void setResult(final double newResult, final int iterationCount) {
+ this.result = newResult;
+ this.iterationCount = iterationCount;
+ this.resultComputed = true;
+ }
+
+ /**
+ * Convenience function for implementations.
+ *
+ * @param x the result to set
+ * @param fx the result to set
+ * @param iterationCount the iteration count to set
+ */
+ protected final void setResult(final double x, final double fx,
+ final int iterationCount) {
+ this.result = x;
+ this.functionValue = fx;
+ this.iterationCount = iterationCount;
+ this.resultComputed = true;
+ }
+
+ /**
+ * Convenience function for implementations.
+ */
+ protected final void clearResult() {
+ this.iterationCount = 0;
+ this.resultComputed = false;
+ }
+
+ /**
+ * Returns true iff the function takes opposite signs at the endpoints.
+ *
+ * @param lower the lower endpoint
+ * @param upper the upper endpoint
+ * @param function the function
+ * @return true if f(lower) * f(upper) < 0
+ * @throws FunctionEvaluationException if an error occurs evaluating the function at the endpoints
+ */
+ protected boolean isBracketing(final double lower, final double upper,
+ final UnivariateRealFunction function)
+ throws FunctionEvaluationException {
+ final double f1 = function.value(lower);
+ final double f2 = function.value(upper);
+ return (f1 > 0 && f2 < 0) || (f1 < 0 && f2 > 0);
+ }
+
+ /**
+ * Returns true if the arguments form a (strictly) increasing sequence
+ *
+ * @param start first number
+ * @param mid second number
+ * @param end third number
+ * @return true if the arguments form an increasing sequence
+ */
+ protected boolean isSequence(final double start, final double mid, final double end) {
+ return (start < mid) && (mid < end);
+ }
+
+ /**
+ * Verifies that the endpoints specify an interval,
+ * throws IllegalArgumentException if not
+ *
+ * @param lower lower endpoint
+ * @param upper upper endpoint
+ * @throws IllegalArgumentException
+ */
+ protected void verifyInterval(final double lower, final double upper) {
+ if (lower >= upper) {
+ throw MathRuntimeException.createIllegalArgumentException(
+ LocalizedFormats.ENDPOINTS_NOT_AN_INTERVAL,
+ lower, upper);
+ }
+ }
+
+ /**
+ * Verifies that <code>lower < initial < upper</code>
+ * throws IllegalArgumentException if not
+ *
+ * @param lower lower endpoint
+ * @param initial initial value
+ * @param upper upper endpoint
+ * @throws IllegalArgumentException
+ */
+ protected void verifySequence(final double lower, final double initial, final double upper) {
+ if (!isSequence(lower, initial, upper)) {
+ throw MathRuntimeException.createIllegalArgumentException(
+ LocalizedFormats.INVALID_INTERVAL_INITIAL_VALUE_PARAMETERS,
+ lower, initial, upper);
+ }
+ }
+
+ /**
+ * Verifies that the endpoints specify an interval and the function takes
+ * opposite signs at the endpoints, throws IllegalArgumentException if not
+ *
+ * @param lower lower endpoint
+ * @param upper upper endpoint
+ * @param function function
+ * @throws IllegalArgumentException
+ * @throws FunctionEvaluationException if an error occurs evaluating the function at the endpoints
+ */
+ protected void verifyBracketing(final double lower, final double upper,
+ final UnivariateRealFunction function)
+ throws FunctionEvaluationException {
+
+ verifyInterval(lower, upper);
+ if (!isBracketing(lower, upper, function)) {
+ throw MathRuntimeException.createIllegalArgumentException(
+ LocalizedFormats.SAME_SIGN_AT_ENDPOINTS,
+ lower, upper, function.value(lower), function.value(upper));
+ }
+ }
+}