Mercurial > dive4elements > river
comparison flys-artifacts/src/main/java/de/intevation/flys/artifacts/model/WstValueTable.java @ 677:a95f34f1f39a
Added error reporting to 'Abflusskurve' calculation.
flys-artifacts/trunk@2101 c6561f87-3c4e-4783-a992-168aeb5c3f6f
author | Sascha L. Teichmann <sascha.teichmann@intevation.de> |
---|---|
date | Fri, 10 Jun 2011 14:24:15 +0000 |
parents | c501f27c1f71 |
children | 19a3185822a4 |
comparison
equal
deleted
inserted
replaced
676:c501f27c1f71 | 677:a95f34f1f39a |
---|---|
15 import org.apache.commons.math.analysis.interpolation.SplineInterpolator; | 15 import org.apache.commons.math.analysis.interpolation.SplineInterpolator; |
16 | 16 |
17 import org.apache.commons.math.analysis.polynomials.PolynomialSplineFunction; | 17 import org.apache.commons.math.analysis.polynomials.PolynomialSplineFunction; |
18 | 18 |
19 import org.apache.commons.math.ArgumentOutsideDomainException; | 19 import org.apache.commons.math.ArgumentOutsideDomainException; |
20 | |
21 import org.apache.commons.math.exception.MathIllegalArgumentException; | |
20 | 22 |
21 public class WstValueTable | 23 public class WstValueTable |
22 implements Serializable | 24 implements Serializable |
23 { | 25 { |
24 private static Logger log = Logger.getLogger(WstValueTable.class); | 26 private static Logger log = Logger.getLogger(WstValueTable.class); |
142 | 144 |
143 public double [][] interpolateWQ( | 145 public double [][] interpolateWQ( |
144 Row other, | 146 Row other, |
145 double km, | 147 double km, |
146 int steps, | 148 int steps, |
147 WstValueTable table | 149 WstValueTable table, |
150 Calculation errors | |
148 ) { | 151 ) { |
149 int W = Math.min(ws.length, other.ws.length); | 152 int W = Math.min(ws.length, other.ws.length); |
150 | 153 |
151 if (W < 1) { | 154 if (W < 1) { |
155 if (errors != null) { | |
156 // TODO: I18N | |
157 errors.addProblem("no ws found"); | |
158 } | |
152 return new double[2][0]; | 159 return new double[2][0]; |
153 } | 160 } |
154 | 161 |
155 double factor = Linear.factor(km, this.km, other.km); | 162 double factor = Linear.factor(km, this.km, other.km); |
156 | 163 |
165 double wqs = Linear.weight( | 172 double wqs = Linear.weight( |
166 factor, | 173 factor, |
167 table.getQIndex(i, km), | 174 table.getQIndex(i, km), |
168 table.getQIndex(i, other.km)); | 175 table.getQIndex(i, other.km)); |
169 | 176 |
177 if (Double.isNaN(wws) || Double.isNaN(wqs)) { | |
178 if (errors != null) { | |
179 // TODO: I18N | |
180 errors.addProblem(km, "cannot find w or q"); | |
181 } | |
182 } | |
183 else { | |
184 if (wqs < minQ) minQ = wqs; | |
185 if (wqs > maxQ) maxQ = wqs; | |
186 } | |
187 | |
170 splineW[i] = wws; | 188 splineW[i] = wws; |
171 splineQ[i] = wqs; | 189 splineQ[i] = wqs; |
172 if (wqs < minQ) minQ = wqs; | |
173 if (wqs > maxQ) maxQ = wqs; | |
174 } | 190 } |
175 | 191 |
176 double stepWidth = (maxQ - minQ)/steps; | 192 double stepWidth = (maxQ - minQ)/steps; |
177 | 193 |
178 SplineInterpolator interpolator = new SplineInterpolator(); | 194 SplineInterpolator interpolator = new SplineInterpolator(); |
179 PolynomialSplineFunction spline = | 195 PolynomialSplineFunction spline; |
180 interpolator.interpolate(splineQ, splineW); | 196 |
197 try { | |
198 spline = interpolator.interpolate(splineQ, splineW); | |
199 } | |
200 catch (MathIllegalArgumentException miae) { | |
201 if (errors != null) { | |
202 // TODO: I18N | |
203 errors.addProblem(km, "spline creation failed"); | |
204 } | |
205 log.error("spline creation failed"); | |
206 return new double[2][0]; | |
207 } | |
181 | 208 |
182 double [] outWs = new double[steps]; | 209 double [] outWs = new double[steps]; |
183 double [] outQs = new double[steps]; | 210 double [] outQs = new double[steps]; |
211 | |
212 Arrays.fill(outWs, Double.NaN); | |
213 Arrays.fill(outQs, Double.NaN); | |
184 | 214 |
185 try { | 215 try { |
186 double q = minQ; | 216 double q = minQ; |
187 for (int i = 0; i < outWs.length; ++i, q += stepWidth) { | 217 for (int i = 0; i < outWs.length; ++i, q += stepWidth) { |
188 outWs[i] = spline.value(outQs[i] = q); | 218 outWs[i] = spline.value(outQs[i] = q); |
189 } | 219 } |
190 } | 220 } |
191 catch (ArgumentOutsideDomainException aode) { | 221 catch (ArgumentOutsideDomainException aode) { |
192 log.error("Spline interpolation failed.", aode); | 222 if (errors != null) { |
223 // TODO: I18N | |
224 errors.addProblem(km, "spline interpolation failed"); | |
225 } | |
226 log.error("spline interpolation failed", aode); | |
193 } | 227 } |
194 | 228 |
195 return new double [][] { outWs, outQs }; | 229 return new double [][] { outWs, outQs }; |
196 } | 230 } |
197 | 231 |
198 public double [][] interpolateWQ(int steps, WstValueTable table) { | 232 public double [][] interpolateWQ( |
199 | 233 int steps, |
234 WstValueTable table, | |
235 Calculation errors | |
236 ) { | |
200 int W = ws.length; | 237 int W = ws.length; |
201 | 238 |
202 if (W < 1) { | 239 if (W < 1) { |
240 if (errors != null) { | |
241 // TODO: I18N | |
242 errors.addProblem(km, "no ws found"); | |
243 } | |
203 return new double[2][0]; | 244 return new double[2][0]; |
204 } | 245 } |
205 | 246 |
206 double [] splineQ = new double[W]; | 247 double [] splineQ = new double[W]; |
207 | 248 |
208 double minQ = Double.MAX_VALUE; | 249 double minQ = Double.MAX_VALUE; |
209 double maxQ = -Double.MAX_VALUE; | 250 double maxQ = -Double.MAX_VALUE; |
210 | 251 |
211 QPosition qPosition = new QPosition(); | |
212 | |
213 for (int i = 0; i < W; ++i) { | 252 for (int i = 0; i < W; ++i) { |
214 splineQ[i] = table.getQIndex(i, km); | 253 double sq = table.getQIndex(i, km); |
215 if (splineQ[i] < minQ) minQ = splineQ[i]; | 254 if (Double.isNaN(sq)) { |
216 if (splineQ[i] > maxQ) maxQ = splineQ[i]; | 255 if (errors != null) { |
256 // TODO: I18N | |
257 errors.addProblem( | |
258 km, "no q found in " + (i+1) + " column"); | |
259 } | |
260 } | |
261 else { | |
262 if (sq < minQ) minQ = sq; | |
263 if (sq > maxQ) maxQ = sq; | |
264 } | |
265 splineQ[i] = sq; | |
217 } | 266 } |
218 | 267 |
219 double stepWidth = (maxQ - minQ)/steps; | 268 double stepWidth = (maxQ - minQ)/steps; |
220 | 269 |
221 SplineInterpolator interpolator = new SplineInterpolator(); | 270 SplineInterpolator interpolator = new SplineInterpolator(); |
222 | 271 |
223 PolynomialSplineFunction spline = | 272 PolynomialSplineFunction spline; |
224 interpolator.interpolate(splineQ, ws); | 273 |
274 try { | |
275 spline = interpolator.interpolate(splineQ, ws); | |
276 } | |
277 catch (MathIllegalArgumentException miae) { | |
278 if (errors != null) { | |
279 // TODO: I18N | |
280 errors.addProblem(km, "spline creation failed"); | |
281 } | |
282 log.error("spline creation failed"); | |
283 return new double[2][0]; | |
284 } | |
225 | 285 |
226 double [] outWs = new double[steps]; | 286 double [] outWs = new double[steps]; |
227 double [] outQs = new double[steps]; | 287 double [] outQs = new double[steps]; |
288 | |
289 Arrays.fill(outWs, Double.NaN); | |
290 Arrays.fill(outQs, Double.NaN); | |
228 | 291 |
229 try { | 292 try { |
230 double q = minQ; | 293 double q = minQ; |
231 for (int i = 0; i < outWs.length; ++i, q += stepWidth) { | 294 for (int i = 0; i < outWs.length; ++i, q += stepWidth) { |
232 outWs[i] = spline.value(outQs[i] = q); | 295 outWs[i] = spline.value(outQs[i] = q); |
233 } | 296 } |
234 } | 297 } |
235 catch (ArgumentOutsideDomainException aode) { | 298 catch (ArgumentOutsideDomainException aode) { |
236 log.error("Spline interpolation failed.", aode); | 299 if (errors != null) { |
300 // TODO: I18N | |
301 errors.addProblem(km, "spline interpolation failed"); | |
302 } | |
303 log.error("spline interpolation failed.", aode); | |
237 } | 304 } |
238 | 305 |
239 return new double [][] { outWs, outQs }; | 306 return new double [][] { outWs, outQs }; |
240 } | 307 } |
241 | 308 |
335 | 402 |
336 if (rowIndex < 1 || rowIndex >= rows.size()) { | 403 if (rowIndex < 1 || rowIndex >= rows.size()) { |
337 // do not extrapolate | 404 // do not extrapolate |
338 Arrays.fill(ws, Double.NaN); | 405 Arrays.fill(ws, Double.NaN); |
339 if (errors != null) { | 406 if (errors != null) { |
407 // TODO: I18N | |
340 errors.addProblem(km, "km not found"); | 408 errors.addProblem(km, "km not found"); |
341 } | 409 } |
342 } | 410 } |
343 else { | 411 else { |
344 Row r1 = rows.get(rowIndex-1); | 412 Row r1 = rows.get(rowIndex-1); |
349 | 417 |
350 return ws; | 418 return ws; |
351 } | 419 } |
352 | 420 |
353 public double [][] interpolateWQ(double km) { | 421 public double [][] interpolateWQ(double km) { |
354 return interpolateWQ(km, DEFAULT_Q_STEPS); | 422 return interpolateWQ(km, null); |
355 } | 423 } |
356 | 424 |
357 public double [][] interpolateWQ(double km, int steps) { | 425 public double [][] interpolateWQ(double km, Calculation errors) { |
426 return interpolateWQ(km, DEFAULT_Q_STEPS, errors); | |
427 } | |
428 | |
429 public double [][] interpolateWQ(double km, int steps, Calculation errors) { | |
358 | 430 |
359 int rowIndex = Collections.binarySearch(rows, new Row(km)); | 431 int rowIndex = Collections.binarySearch(rows, new Row(km)); |
360 | 432 |
361 if (rowIndex >= 0) { // direct row match | 433 if (rowIndex >= 0) { // direct row match |
362 Row row = rows.get(rowIndex); | 434 Row row = rows.get(rowIndex); |
363 return row.interpolateWQ(steps, this); | 435 return row.interpolateWQ(steps, this, errors); |
364 } | 436 } |
365 | 437 |
366 rowIndex = -rowIndex -1; | 438 rowIndex = -rowIndex -1; |
367 | 439 |
368 if (rowIndex < 1 || rowIndex >= rows.size()) { | 440 if (rowIndex < 1 || rowIndex >= rows.size()) { |
369 // do not extrapolate | 441 // do not extrapolate |
442 if (errors != null) { | |
443 // TODO: I18N | |
444 errors.addProblem(km, "km not found"); | |
445 } | |
370 return new double[2][0]; | 446 return new double[2][0]; |
371 } | 447 } |
372 | 448 |
373 Row r1 = rows.get(rowIndex-1); | 449 Row r1 = rows.get(rowIndex-1); |
374 Row r2 = rows.get(rowIndex); | 450 Row r2 = rows.get(rowIndex); |
375 | 451 |
376 return r1.interpolateWQ(r2, km, steps, this); | 452 return r1.interpolateWQ(r2, km, steps, this, errors); |
377 } | 453 } |
378 | 454 |
379 public boolean interpolate( | 455 public boolean interpolate( |
380 double km, | 456 double km, |
381 double [] out, | 457 double [] out, |