# HG changeset patch # User Sascha L. Teichmann # Date 1329748588 0 # Node ID ba35dfb7c09aedda3584afa4fc5fad57c6d25f3f # Parent b3f6d49cdc805dc99f133a6217942e82ffb6a18d FixingsOverview: Construct the Q sectors once. flys-artifacts/trunk@4088 c6561f87-3c4e-4783-a992-168aeb5c3f6f diff -r b3f6d49cdc80 -r ba35dfb7c09a flys-artifacts/ChangeLog --- a/flys-artifacts/ChangeLog Sun Feb 19 17:14:39 2012 +0000 +++ b/flys-artifacts/ChangeLog Mon Feb 20 14:36:28 2012 +0000 @@ -1,3 +1,10 @@ +2012-02-20 Sascha L. Teichmann + + * src/main/java/de/intevation/flys/artifacts/model/FixingsOverview.java: + Refactored to build the Q sectors once at construction time and not + every time output is generated. + This will ease the job of applying filters to the Overview. + 2012-02-19 Sascha L. Teichmann Service to generate the data needed to build the "Fixerungen pro Fluss Uebersicht" diff -r b3f6d49cdc80 -r ba35dfb7c09a flys-artifacts/src/main/java/de/intevation/flys/artifacts/model/FixingsOverview.java --- a/flys-artifacts/src/main/java/de/intevation/flys/artifacts/model/FixingsOverview.java Sun Feb 19 17:14:39 2012 +0000 +++ b/flys-artifacts/src/main/java/de/intevation/flys/artifacts/model/FixingsOverview.java Mon Feb 20 14:36:28 2012 +0000 @@ -119,7 +119,7 @@ " MAX(position) AS stop_km " + "FROM" + " wst_column_values " + - "WHERE " + + "WHERE" + " wst_column_id = :column_id"; public static class Range implements Serializable { @@ -135,10 +135,22 @@ this.end = end; } + public double getStart() { + return start; + } + + public double getEnd() { + return end; + } + public boolean disjoint(Range other) { return start > other.end || other.start > end; } + public boolean intersects(Range other) { + return !disjoint(other); + } + public boolean clip(Range other) { if (disjoint(other)) return false; @@ -229,6 +241,91 @@ } } // class GaugeRange + public static class GaugeFinder { + + protected List gauges; + protected boolean isKmUp; + + public GaugeFinder(List gauges) { + this(gauges, true); + } + + public GaugeFinder( + List gauges, + boolean isKmUp + ) { + this.gauges = gauges; + this.isKmUp = isKmUp; + } + + public boolean getIsKmUp() { + return isKmUp; + } + + public void setIsKmUp(boolean isKmUp) { + this.isKmUp = isKmUp; + } + + public GaugeRange find(Range range) { + double km = isKmUp ? range.start : range.end; + for (GaugeRange gauge: gauges) { + if (gauge.inside(km)) { + return gauge; + } + } + return null; + } + + public GaugeRange find(int gaugeId) { + for (GaugeRange gauge: gauges) { + if (gauge.gaugeId == gaugeId) { + return gauge; + } + } + return null; + } + + public boolean loadDischargeSectors(Session session, int riverId) { + + SQLQuery query = session.createSQLQuery(SQL_DISCHARGE_SECTORS) + .addScalar("gauge_id", StandardBasicTypes.INTEGER) + .addScalar("name", StandardBasicTypes.STRING) + .addScalar("value", StandardBasicTypes.DOUBLE); + + query.setInteger("river_id", riverId); + + List list = query.list(); + + if (list.isEmpty()) { + log.warn("River " + riverId + " has no discharge sectors."); + return false; + } + + GaugeRange gauge = null; + + for (Object [] row: list) { + int gaugeId = (Integer)row[0]; + String label = (String) row[1]; + Double value = (Double) row[2]; + + if (gauge == null || gauge.gaugeId != gaugeId) { + if ((gauge = find(gaugeId)) == null) { + log.warn("Cannot find gauge for id " + gaugeId + "."); + continue; + } + } + + gauge.addMainValue(label, value); + } + + for (GaugeRange g: gauges) { + g.buildClasses(); + } + + return true; + } + } // class GaugeFinder + public static class QRange extends Range { protected double q; @@ -249,11 +346,21 @@ public SectorRange() { } + public SectorRange(SectorRange other) { + start = other.start; + end = other.end; + sector = other.sector; + } + public SectorRange(double start, double end, int sector) { super(start, end); this.sector = sector; } + public int getSector() { + return sector; + } + public boolean enlarge(SectorRange other) { if (sector == other.sector && Math.abs(end-other.start) < EPSILON2) { @@ -280,7 +387,7 @@ protected Date startTime; protected String name; - protected List qRanges; + protected List sectors; public Column() { } @@ -290,16 +397,18 @@ this.startTime = startTime; this.name = name; - qRanges = new ArrayList(); + sectors = new ArrayList(); } public Fixing getFixing() { return Fixing.this; } - public List classify(GaugeRange gauge) { + public List getSectors() { + return sectors; + } - List sectors = new ArrayList(); + public void buildSectors(GaugeRange gauge, List qRanges) { for (QRange qRange: qRanges) { SectorRange sector = new SectorRange( @@ -310,8 +419,6 @@ sectors.add(sector); } } - - return sectors; } public void loadKmRange(SQLQuery query) { @@ -329,10 +436,15 @@ } } - public void loadQRanges(SQLQuery query) { + public void loadQRanges( + SQLQuery query, + GaugeFinder gaugeFinder + ) { query.setInteger("column_id", columnId); List list = query.list(); + List qRanges = new ArrayList(list.size()); + for (Object [] row: list) { double q = (Double)row[0]; double start = (Double)row[1]; @@ -342,11 +454,20 @@ qRanges.add(qRange); } } + + GaugeRange gauge = gaugeFinder.find(this); + + if (gauge != null) { + buildSectors(gauge, qRanges); + } + else { + log.warn("No gauge found for column " + columnId + "."); + } } } // class Column - protected int wstId; - protected String description; + protected int wstId; + protected String description; protected List columns; public Fixing() { @@ -375,27 +496,32 @@ } } - public void loadColumnsQRanges(SQLQuery query) { + public void loadColumnsQRanges( + SQLQuery query, + GaugeFinder gaugeFinder + ) { for (Column column: columns) { - column.loadQRanges(query); + column.loadQRanges(query, gaugeFinder); } } - public void addAllColumns(List allColumns) { - allColumns.addAll(columns); + public void addAllColumns(List allColumns, Range range) { + for (Column column: columns) { + if (column.intersects(range)) { + allColumns.add(column); + } + } } } // class Fixing - protected String riverName; - protected int riverId; - protected boolean isKmUp; - protected List gauges; - protected List fixings; - protected Range extent; + protected String riverName; + protected int riverId; + protected boolean isKmUp; + protected List fixings; + protected Range extent; public FixingsOverview() { - gauges = new ArrayList(); fixings = new ArrayList(); } @@ -446,8 +572,7 @@ return true; } - - protected boolean loadGauges(Session session) { + protected GaugeFinder loadGauges(Session session) { SQLQuery query = session.createSQLQuery(SQL_GAUGES) .addScalar("gauge_id", StandardBasicTypes.INTEGER) .addScalar("a", StandardBasicTypes.DOUBLE) @@ -459,9 +584,11 @@ if (list.isEmpty()) { log.warn("River " + riverId + " has no gauges."); - return false; + return null; } + List gauges = new ArrayList(); + for (Object [] row: list) { int gaugeId = (Integer)row[0]; double start = (Double) row[1]; @@ -470,66 +597,9 @@ gauges.add(gauge); } - return true; - } - - protected GaugeRange findGaugeById(int gaugeId) { - for (GaugeRange gauge: gauges) { - if (gauge.gaugeId == gaugeId) { - return gauge; - } - } - return null; - } - - protected GaugeRange findGaugeByKm(double km) { - for (GaugeRange gauge: gauges) { - if (gauge.inside(km)) { - return gauge; - } - } - return null; + return new GaugeFinder(gauges, isKmUp); } - protected boolean loadDischargeSectors(Session session) { - - SQLQuery query = session.createSQLQuery(SQL_DISCHARGE_SECTORS) - .addScalar("gauge_id", StandardBasicTypes.INTEGER) - .addScalar("name", StandardBasicTypes.STRING) - .addScalar("value", StandardBasicTypes.DOUBLE); - - query.setInteger("river_id", riverId); - - List list = query.list(); - - if (list.isEmpty()) { - log.warn("River " + riverId + " has no discharge sectors."); - return false; - } - - GaugeRange gauge = null; - - for (Object [] row: list) { - int gaugeId = (Integer)row[0]; - String label = (String) row[1]; - Double value = (Double) row[2]; - - if (gauge == null || gauge.gaugeId != gaugeId) { - if ((gauge = findGaugeById(gaugeId)) == null) { - log.warn("Cannot find gauge for id " + gaugeId + "."); - continue; - } - } - - gauge.addMainValue(label, value); - } - - for (GaugeRange g: gauges) { - g.buildClasses(); - } - - return true; - } protected void loadFixings(Session session) { SQLQuery query = session.createSQLQuery(SQL_FIXINGS) @@ -574,49 +644,55 @@ } } - protected void loadFixingsColumnsQRanges(Session session) { + protected void loadFixingsColumnsQRanges( + Session session, + GaugeFinder gaugeFinder + ) { SQLQuery query = session.createSQLQuery(SQL_FIXING_COLUMN_Q_RANGES) .addScalar("q", StandardBasicTypes.DOUBLE) .addScalar("start_km", StandardBasicTypes.DOUBLE) .addScalar("stop_km", StandardBasicTypes.DOUBLE); for (Fixing fixing: fixings) { - fixing.loadColumnsQRanges(query); + fixing.loadColumnsQRanges(query, gaugeFinder); } } public boolean load(Session session) { - if (!loadRiver(session)) { + if (!loadRiver(session) + || !loadRiverExtent(session)) { return false; } - if (!loadRiverExtent(session)) { - return false; - } + GaugeFinder gaugeFinder = loadGauges(session); - if (!loadGauges(session)) { - return false; - } - - if (!loadDischargeSectors(session)) { + if (gaugeFinder == null + || !gaugeFinder.loadDischargeSectors(session, riverId)) { return false; } loadFixings(session); loadFixingsColumns(session); loadFixingsColumnsKmRange(session); - loadFixingsColumnsQRanges(session); + loadFixingsColumnsQRanges(session, gaugeFinder); return true; } + private static final Range FULL_EXTENT = + new Range(-Double.MAX_VALUE, Double.MAX_VALUE); + public void generateOverview(Document document) { + generateOverview(document, FULL_EXTENT); + } + + public void generateOverview(Document document, Range range) { List allColumns = new ArrayList(); for (Fixing fixing: fixings) { - fixing.addAllColumns(allColumns); + fixing.addAllColumns(allColumns, range); } Collections.sort(allColumns, Fixing.DATE_CMP); @@ -637,16 +713,8 @@ for (Fixing.Column column: allColumns) { - double km = isKmUp ? column.start : column.end; - - GaugeRange gauge = findGaugeByKm(km); - - if (gauge == null) { - log.warn("Cannot find gauge for km " + km + "."); - continue; - } - - List sectors = column.classify(gauge); + // TODO: Apply additional filters here. + List sectors = column.getSectors(); if (!sectors.isEmpty()) { Element eE = document.createElement("event");