diff flys-artifacts/src/main/java/org/dive4elements/river/artifacts/model/sq/SQRelationCalculation.java @ 5831:bd047b71ab37

Repaired internal references
author Sascha L. Teichmann <teichmann@intevation.de>
date Thu, 25 Apr 2013 12:06:39 +0200
parents flys-artifacts/src/main/java/de/intevation/flys/artifacts/model/sq/SQRelationCalculation.java@aaf810d4ec82
children
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/flys-artifacts/src/main/java/org/dive4elements/river/artifacts/model/sq/SQRelationCalculation.java	Thu Apr 25 12:06:39 2013 +0200
@@ -0,0 +1,194 @@
+package org.dive4elements.river.artifacts.model.sq;
+
+import org.dive4elements.river.artifacts.access.SQRelationAccess;
+
+import org.dive4elements.river.artifacts.math.fitting.Function;
+import org.dive4elements.river.artifacts.math.fitting.FunctionFactory;
+
+import org.dive4elements.river.artifacts.model.Calculation;
+import org.dive4elements.river.artifacts.model.CalculationResult;
+import org.dive4elements.river.artifacts.model.DateRange;
+import org.dive4elements.river.artifacts.model.Parameters;
+
+import org.dive4elements.river.backend.SedDBSessionHolder;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.log4j.Logger;
+
+public class SQRelationCalculation extends Calculation {
+
+    private static final Logger log =
+        Logger.getLogger(SQRelationCalculation.class);
+
+    public static final String SQ_FUNCTION_NAME = "sq-pow";
+
+    protected String    river;
+    protected double    location;
+    protected DateRange period;
+    protected double    outliers;
+    private   String    method;
+
+    public SQRelationCalculation() {
+    }
+
+    public SQRelationCalculation(SQRelationAccess access) {
+
+        String    river    = access.getRiver();
+        Double    location = access.getLocation();
+        DateRange period   = access.getPeriod();
+        Double    outliers = access.getOutliers();
+        String    method   = access.getOutlierMethod();
+
+        //river = "Rhein";
+
+        if (river == null) {
+            // TODO: i18n
+            addProblem("sq.missing.river");
+        }
+
+        if (location == null) {
+            // TODO: i18n
+            addProblem("sq.missing.location");
+        }
+
+        if (period == null) {
+            // TODO: i18n
+            addProblem("sq.missing.periods");
+        }
+
+        if (outliers == null) {
+            // TODO: i18n
+            addProblem("sq.missing.outliers");
+        }
+
+        if (method == null) {
+            //TODO: i18n
+            addProblem("sq.missing.method");
+        }
+
+        if (!hasProblems()) {
+            this.river    = river;
+            this.location = location;
+            this.period   = period;
+            this.outliers = outliers;
+            this.method   = method;
+        }
+    }
+
+
+    public CalculationResult calculate() {
+        log.debug("SQRelationCalculation.calculate");
+
+        if (hasProblems()) {
+            return new CalculationResult(this);
+        }
+
+        SedDBSessionHolder.acquire();
+        try {
+            return internalCalculate();
+        }
+        finally {
+            SedDBSessionHolder.release();
+        }
+    }
+
+    protected CalculationResult internalCalculate() {
+
+        Function function = FunctionFactory
+            .getInstance()
+            .getFunction(SQ_FUNCTION_NAME);
+
+        if (function == null) {
+            log.error("No '" + SQ_FUNCTION_NAME + "' function found.");
+            // TODO: i18n
+            addProblem("sq.missing.sq.function");
+        }
+
+        Measurements measurements =
+            MeasurementFactory.getMeasurements(river, location, period);
+
+        SQFractionResult [] fractionResults =
+            new SQFractionResult[SQResult.NUMBER_FRACTIONS];
+
+        for (int i = 0; i < fractionResults.length; ++i) {
+            List<SQ> sqs = measurements.getSQs(i);
+
+            SQFractionResult fractionResult;
+
+            List<SQFractionResult.Iteration> iterations =
+                doFitting(function, sqs);
+
+            if (iterations == null) {
+                // TODO: i18n
+                addProblem("sq.fitting.failed." + i);
+                fractionResult = new SQFractionResult();
+            }
+            else {
+                fractionResult = new SQFractionResult(
+                    sqs.toArray(new SQ[sqs.size()]),
+                    iterations);
+            }
+
+            fractionResults[i] = fractionResult;
+        }
+
+        return new CalculationResult(
+            new SQResult[] { new SQResult(location, fractionResults) },
+            this);
+    }
+
+    protected List<SQFractionResult.Iteration> doFitting(
+        final Function function,
+        List<SQ> sqs
+    ) {
+        final List<SQFractionResult.Iteration> iterations =
+            new ArrayList<SQFractionResult.Iteration>();
+
+        boolean success = new Fitting(function, outliers).fit(
+            sqs,
+            method,
+            new Fitting.Callback() {
+                @Override
+                public void afterIteration(
+                    double [] coeffs,
+                    SQ []     measurements,
+                    SQ []     outliers,
+                    double    standardDeviation,
+                    double    chiSqr
+                ) {
+                    Parameters parameters = createParameters(
+                        function.getParameterNames(),
+                        coeffs,
+                        standardDeviation,
+                        chiSqr);
+                    iterations.add(new SQFractionResult.Iteration(
+                        parameters,
+                        measurements,
+                        outliers));
+                }
+            });
+
+        return success ? iterations : null;
+    }
+
+    public static final Parameters createParameters(
+        String [] names,
+        double [] values,
+        double    standardDeviation,
+        double    chiSqr
+    ) {
+        String [] columns = new String[names.length + 2];
+        columns[0] = "chi_sqr";
+        columns[1] = "std_dev";
+        System.arraycopy(names, 0, columns, 2, names.length);
+        Parameters parameters = new Parameters(columns);
+        int row = parameters.newRow();
+        parameters.set(row, names, values);
+        parameters.set(row, "chi_sqr", chiSqr);
+        parameters.set(row, "std_dev", standardDeviation);
+        return parameters;
+    }
+}
+// vim:set ts=4 sw=4 si et sta sts=4 fenc=utf-8 :

http://dive4elements.wald.intevation.org