diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/application/VdypComponent.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/application/VdypComponent.java index ec37e65b1..496437027 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/application/VdypComponent.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/application/VdypComponent.java @@ -8,7 +8,6 @@ import java.time.LocalTime; import java.util.Properties; -@SuppressWarnings({ "java:S100", "java:S116" }) public class VdypComponent { private static final String COPYRIGHT_HOLDER = "Government of British Columbia"; diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/application/VdypStartApplication.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/application/VdypStartApplication.java index e3c64d77e..be0fd9614 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/application/VdypStartApplication.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/application/VdypStartApplication.java @@ -383,13 +383,6 @@ protected List findPrimarySpecies(Collection allSpecies) { * @return * @throws ProcessingException */ - @SuppressWarnings( - { // - "java:S1301", // Using switch instead of if for consistency - "java:S3776" // Inherently a lot of branching in a consistent manner, breaking into more - // functions would make it less comprehensible - } - ) protected int findItg(List primarySecondary) throws StandProcessingException { var primary = primarySecondary.get(0); @@ -747,7 +740,6 @@ public static Coefficients weightedCoefficientSum( } // FIPLAND - @SuppressWarnings("java:S3655") public float estimatePercentForestLand(P polygon, Optional vetLayer, L primaryLayer) throws ProcessingException { if (polygon.getPercentAvailable().isPresent()) { return polygon.getPercentAvailable().get(); diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ComputationMethods.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ComputationMethods.java index 0bc01e772..f18583a34 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ComputationMethods.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ComputationMethods.java @@ -76,12 +76,12 @@ public ComputationMethods(EstimationMethods estimationMethods, VdypApplicationId } /** - * YUC1 - compute Utilization components (quad-mean-diameter, basal area and trees-per-hectare) and, - * optionally, volumes for a polygon's primary layer. - * - * @param bec Bec zone - * @param vdypLayer (primary) layer in question - * @param volumeComputeMode the {@link VolumeComputeMode} under which this method is to operate + * YUC1 - compute Utilization components (quad-mean-diameter, basal area and trees-per-hectare) and, optionally, + * volumes for a polygon's primary layer. + * + * @param bec Bec zone + * @param vdypLayer (primary) layer in question + * @param volumeComputeMode the {@link VolumeComputeMode} under which this method is to operate * @param compatibilityVariableMode the {@link CompatibilityVariableMode} under which this method is to operate. * @throws ProcessingException */ diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/EstimationMethods.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/EstimationMethods.java index 4fbda08c4..8b31675f9 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/EstimationMethods.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/EstimationMethods.java @@ -889,7 +889,7 @@ public float estimateBaseAreaYield( * @throws StandProcessingException in the event of a processing error */ public float estimateQuadMeanDiameterYield( - Coefficients coefficients, int controlVariable2Setting, float dominantHeight, float breastHeightAge, + Coefficients coefficients, int debugVariable2Value, float dominantHeight, float breastHeightAge, Optional veteranBaseArea, float upperBoundQuadMeanDiameter ) throws StandProcessingException { @@ -897,7 +897,10 @@ public float estimateQuadMeanDiameterYield( return 7.6f; } - final float ageUse = breastHeightAge; + float ageUse = breastHeightAge; + if (debugVariable2Value > 0) { + ageUse = Math.min(ageUse, debugVariable2Value * 100.0f); + } if (ageUse <= 0f) { throw new StandProcessingException("Primary breast height age must be positive but was " + ageUse); @@ -909,8 +912,8 @@ public float estimateQuadMeanDiameterYield( final float c1 = Math.max(coefficients.getCoe(1) + coefficients.getCoe(2) * trAge, 0f); final float c2 = Math.max(coefficients.getCoe(3) + coefficients.getCoe(4) * trAge, 0f); - float dq = c0 + c1 * FloatMath.pow(dominantHeight - 5f, c2); - + float dq = c0 + c1 * FloatMath.pow(dominantHeight - 5f, c2) + * FloatMath.exp(veteranBaseArea.orElse(0.0f) * coefficients.getCoe(5)); return FloatMath.clamp(dq, 7.6f, upperBoundQuadMeanDiameter); } diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ReconcilationMethods.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ReconcilationMethods.java index 387b0eaf6..a7567c071 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ReconcilationMethods.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ReconcilationMethods.java @@ -80,7 +80,6 @@ public static void reconcileComponents( } } - @SuppressWarnings("java:S3655") public static void reconcileComponentsMode1( UtilizationVector baseAreaUtil, UtilizationVector treesPerHectareUtil, UtilizationVector quadMeanDiameterUtil, float tphSumHigh @@ -250,7 +249,6 @@ public static void reconcileComponentsMode2( } } - @SuppressWarnings("java:S3655") public static void reconcileComponentsMode3( UtilizationVector baseAreaUtil, UtilizationVector treesPerHectareUtil, UtilizationVector quadMeanDiameterUtil diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/Utils.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/Utils.java index 5d25fcb18..67b8d2f87 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/Utils.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/Utils.java @@ -27,6 +27,7 @@ import ca.bc.gov.nrs.vdyp.model.GenusDefinitionMap; import ca.bc.gov.nrs.vdyp.model.UtilizationClass; import ca.bc.gov.nrs.vdyp.model.UtilizationVector; +import ca.bc.gov.nrs.vdyp.model.VdypEntity; import ca.bc.gov.nrs.vdyp.model.VdypLayer; import ca.bc.gov.nrs.vdyp.model.VdypSpecies; import ca.bc.gov.nrs.vdyp.model.VdypUtilizationHolder; @@ -382,6 +383,37 @@ public static String optPretty(Optional value, Function string return (String) optNa(value.map(stringify)); } + /** + * If f is null or f.isNan() is true, this method returns + * Optional.empty() otherwise, Optional.of(f) is returned. + * + * @param f the Float to be made into an Optional + * @return as described. + */ + public static Optional optFloat(Float f) { + assert VdypEntity.MISSING_FLOAT_VALUE.isNaN(); + if (f == null || f.isNaN()) { + return Optional.empty(); + } else { + return Optional.of(f); + } + } + + /** + * If f is null or f.isNan() is true, this method returns + * Optional.empty() otherwise, Optional.of(f) is returned. + * + * @param i the Float to be made into an Optional + * @return as described. + */ + public static Optional optInt(Integer i) { + if (i == null || i == VdypEntity.MISSING_INTEGER_VALUE) { + return Optional.empty(); + } else { + return Optional.of(i); + } + } + /** * Iterates over all but the last entry, passing them to the first consumer then passes the last entry to the second * consumer diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ValueOrMarker.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ValueOrMarker.java index 65f3e16a6..f77782b40 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ValueOrMarker.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common/ValueOrMarker.java @@ -12,7 +12,6 @@ * @param * @param */ -@SuppressWarnings("java:S119") public class ValueOrMarker { private final boolean isMarker; private final Object obj; diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/AgeToAge.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/AgeToAge.java index c5daaffc0..6b05f4148 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/AgeToAge.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/AgeToAge.java @@ -16,7 +16,6 @@ */ public class AgeToAge { - @SuppressWarnings("java:S3776, java:S6541, java:S1479") public static double ageToAge( SiteIndexEquation cuIndex, double sourceAge, SiteIndexAgeType sourceAgeType, SiteIndexAgeType targetAgeType, double years2BreastHeight diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/Height2SiteIndex.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/Height2SiteIndex.java index 986ff0f51..ea45111fd 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/Height2SiteIndex.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/Height2SiteIndex.java @@ -22,14 +22,12 @@ * Height2SiteIndex.java - given age and height, computes site index. - if age is total, site index and years to breast * height are iterated until stable. */ -@SuppressWarnings("java:S1479") public class Height2SiteIndex { // Taken from sindex.h /* error codes */ private static final int SI_ERR_NO_ANS = -4; - @SuppressWarnings("java:S3776, java:S6541") public static double heightToIndex( SiteIndexEquation cuIndex, double age, SiteIndexAgeType ageType, double height, SiteIndexEstimationType siEstType @@ -91,7 +89,6 @@ public static double heightToIndex( return index; } - @SuppressWarnings("java:S3776, java:S6541") public static double baHeightToIndex(SiteIndexEquation cuIndex, double bhage, double height, SiteIndexEstimationType siEstType) throws CommonCalculatorException { @@ -3756,7 +3753,6 @@ public static double siteIterate(SiteIndexEquation cuIndex, double age, SiteInde } - @SuppressWarnings("java:S3776, java:S6541") public static double huGarciaQ(double siteIndex, double breastHeightAge) { double h, q, step, diff, lastdiff; diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/SiteIndex2Height.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/SiteIndex2Height.java index 2fc70f2ab..7bbb7286b 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/SiteIndex2Height.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/common_calculators/SiteIndex2Height.java @@ -20,7 +20,6 @@ /** * SiteIndex2Height.java - given site index and age, computes site height. */ -@SuppressWarnings("java:S1479") public class SiteIndex2Height { /** @@ -2083,7 +2082,7 @@ private static double wiley( } height = Utils.computeInFeet(siteIndex, siteIndexFt -> { - double x1 = 2500 / (siteIndex - 4.5); + double x1 = 2500 / (siteIndexFt - 4.5); double x2 = -1.7307 + 0.1394 * x1; double x3 = -0.0616 + 0.0137 * x1; diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/parse/coe/HLNonprimaryCoefficientParser.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/parse/coe/HLNonprimaryCoefficientParser.java index f5ef6e8aa..174aa60ee 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/parse/coe/HLNonprimaryCoefficientParser.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/parse/coe/HLNonprimaryCoefficientParser.java @@ -82,9 +82,7 @@ public boolean isIgnoredLine(String line) { speciesIndicies, speciesIndicies, regionIndicies, MatrixMap3Impl.emptyDefault() ); lineParser.parse(is, result, (value, r, line) -> { - @SuppressWarnings("java:S117") var sp0_1 = (String) value.get(NON_PRIMARY_SPECIES_KEY); - @SuppressWarnings("java:S117") var sp0_2 = (String) value.get(PRIMARY_SPECIES_KEY); var ieqn = (Integer) value.get(EQUATION_KEY); var region = (Region) value.get(REGION_KEY); diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/parse/common/ParseEntryHandler.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/parse/common/ParseEntryHandler.java index ade7dc4b1..4612eaea1 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/parse/common/ParseEntryHandler.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/parse/common/ParseEntryHandler.java @@ -13,7 +13,6 @@ * @param */ @FunctionalInterface -@SuppressWarnings("java:S119") public interface ParseEntryHandler { /** diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/write/VdypOutputWriter.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/write/VdypOutputWriter.java index 41ff6de96..4f8c5c19e 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/write/VdypOutputWriter.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/io/write/VdypOutputWriter.java @@ -127,7 +127,7 @@ public void setPolygonYear(int currentYear) { * Write the given polygon record for the given year to the polygon file. * * @param polygon the polygon to be written - * @param year the year of the polygon + * @param year the year of the polygon * @throws IOException */ public void writePolygonWithSpeciesAndUtilizationForYear(VdypPolygon polygon, int year) throws IOException { @@ -143,9 +143,13 @@ public void writePolygonWithSpeciesAndUtilizationForYear(VdypPolygon polygon, in */ // VDYP_OUT when JPROGRAM = 1 (FIPSTART) or 3 (VRISTART) public void writePolygonWithSpeciesAndUtilization(VdypPolygon polygon) throws IOException { - + writePolygon(polygon); - for (var layer : polygon.getLayers().values()) { + + // Primary then Veteran (if present) + var sortedLayers = polygon.getLayers().values().stream() + .sorted((l1, l2) -> l1.getLayerType().getIndex() - l2.getLayerType().getIndex()).toList(); + for (var layer : sortedLayers) { writeUtilization(polygon, layer, layer); List specs = new ArrayList<>(layer.getSpecies().size()); specs.addAll(layer.getSpecies().values()); diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/math/FloatMath.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/math/FloatMath.java index ab1376a3a..ff3461635 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/math/FloatMath.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/math/FloatMath.java @@ -41,7 +41,6 @@ public static float ceil(float f) { return (float) Math.ceil(f); } - @SuppressWarnings("squid:S4274") public static float clamp(float x, float min, float max) { assert max >= min : "Maximum " + max + " was less than minimum " + min; if (x < min) diff --git a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/model/GenusDefinition.java b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/model/GenusDefinition.java index e235e47dc..29c7770c1 100644 --- a/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/model/GenusDefinition.java +++ b/lib/vdyp-common/src/main/java/ca/bc/gov/nrs/vdyp/model/GenusDefinition.java @@ -6,7 +6,6 @@ public class GenusDefinition extends AliasedEntity implements Comparable retainCriteria) - throws ProcessingException { + public Bank(VdypLayer layer, BecDefinition becZone, Predicate retainCriteria) { this.layer = layer; this.becZone = becZone; @@ -185,7 +185,7 @@ void refreshBank(VdypLayer layer) throws ProcessingException { } } - private void transferSpeciesIntoBank(int index, VdypSpecies species) throws ProcessingException { + private void transferSpeciesIntoBank(int index, VdypSpecies species) { speciesNames[index] = species.getGenus(); sp64Distributions[index] = species.getSp64DistributionSet(); @@ -235,13 +235,12 @@ private void transferUtilizationSetIntoBank(int index, VdypUtilizationHolder uh) } /** - * For each species, set uc All to the sum of the UC values, UC 7.5 and above only, - * for the summable values, and calculate quad-mean-diameter from these values. + * For each species, set uc All to the sum of the UC values, UC 7.5 and above only, for the summable values, and + * calculate quad-mean-diameter from these values. *

- * For the layer, set uc All values (for summable types) to the sum of those of the - * individual species and set the other uc values to the sum of those of the - * individual species. Calculate the uc All value for quad-mean-diameter, and the - * uc All and Small value for lorey-height. + * For the layer, set uc All values (for summable types) to the sum of those of the individual species and set the + * other uc values to the sum of those of the individual species. Calculate the uc All value for quad-mean-diameter, + * and the uc All and Small value for lorey-height. */ private void setCalculateUtilizationClassAllValues() { @@ -250,7 +249,7 @@ private void setCalculateUtilizationClassAllValues() { int ucSmallIndex = UtilizationClass.SMALL.ordinal(); // Each species - + for (int sp0Index : indices) { basalAreas[sp0Index][ucAllIndex] = sumUtilizationClassValues( @@ -277,7 +276,7 @@ private void setCalculateUtilizationClassAllValues() { .quadMeanDiameter(basalAreas[sp0Index][ucAllIndex], treesPerHectare[sp0Index][ucAllIndex]); } } - + // Layer basalAreas[layerIndex][ucAllIndex] = sumSpeciesUtilizationClassValues(basalAreas, UtilizationClass.ALL); @@ -366,7 +365,7 @@ private float sumSpeciesUtilizationClassValues(float[][] ucValues, UtilizationCl * * @return as described */ - VdypLayer getLayer() { + VdypLayer buildLayerFromBank() { transferUtilizationsFromBank(0, layer); @@ -375,7 +374,7 @@ VdypLayer getLayer() { newSpecies.add(transferSpeciesFromBank(i, layer.getSpecies().get(speciesNames[i]))); } layer.setSpecies(newSpecies); - + return layer; } @@ -384,15 +383,28 @@ private VdypSpecies transferSpeciesFromBank(int index, VdypSpecies species) { VdypSpecies newSpecies = VdypSpecies.build(speciesBuilder -> { speciesBuilder.copy(species); speciesBuilder.percentGenus(this.percentagesOfForestedLand[index]); - species.getSite().ifPresent(site -> speciesBuilder.addSite(VdypSite.build(siteBuilder -> { + species.getSite().ifPresentOrElse(site -> speciesBuilder.addSite(VdypSite.build(siteBuilder -> { siteBuilder.copy(site); - siteBuilder.ageTotal(this.ageTotals[index]); - siteBuilder.height(this.dominantHeights[index]); - siteBuilder.siteCurveNumber(this.siteCurveNumbers[index]); siteBuilder.siteGenus(this.speciesNames[index]); - siteBuilder.siteIndex(this.siteIndices[index]); - siteBuilder.yearsToBreastHeight(this.yearsToBreastHeight[index]); - }))); + siteBuilder.ageTotal(Utils.optFloat(ageTotals[index])); + siteBuilder.height(Utils.optFloat(this.dominantHeights[index])); + siteBuilder.siteCurveNumber(Utils.optInt(this.siteCurveNumbers[index])); + siteBuilder.siteIndex(Utils.optFloat(this.siteIndices[index])); + siteBuilder.yearsToBreastHeight(Utils.optFloat(this.yearsToBreastHeight[index])); + })), () -> { + VdypSite site = VdypSite.build(siteBuilder -> { + siteBuilder.polygonIdentifier(species.getPolygonIdentifier()); + siteBuilder.layerType(species.getLayerType()); + siteBuilder.siteGenus(this.speciesNames[index]); + siteBuilder.ageTotal(Utils.optFloat(this.ageTotals[index])); + siteBuilder.height(Utils.optFloat(this.dominantHeights[index])); + siteBuilder.siteCurveNumber(Utils.optInt(this.siteCurveNumbers[index])); + siteBuilder.siteIndex(Utils.optFloat(this.siteIndices[index])); + siteBuilder.yearsToBreastHeight(Utils.optFloat(this.yearsToBreastHeight[index])); + }); + + speciesBuilder.addSite(site); + }); }); transferUtilizationsFromBank(index, newSpecies); diff --git a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardDataStreamReader.java b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardDataStreamReader.java index acafec551..a63146bab 100644 --- a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardDataStreamReader.java +++ b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardDataStreamReader.java @@ -89,8 +89,6 @@ public Optional readNextPolygon() throws ProcessingException { // Advance all the streams until the definition for the polygon is found. - Optional thePolygon = Optional.empty(); - try { if (polygonStream.hasNext()) { var polygon = polygonStream.next(); @@ -176,9 +174,9 @@ public Optional readNextPolygon() throws ProcessingException { var key = new UtilizationBySpeciesKey(LayerType.PRIMARY, 0); Map defaultSpeciesUtilization = utilizationsBySpeciesMap .get(key); - + String primarySp0 = getPrimarySpecies(polygon, primaryLayerSpecies.values()).getGenus(); - + primaryLayer = VdypLayer.build(builder -> { builder.layerType(LayerType.PRIMARY); builder.polygonIdentifier(polygon.getPolygonIdentifier()); @@ -215,28 +213,38 @@ public Optional readNextPolygon() throws ProcessingException { polygon.setLayers(layerMap); - thePolygon = Optional.of(polygon); UtilizationOperations.doPostCreateAdjustments(polygon); + + return Optional.of(polygon); + } else { + return Optional.empty(); } } catch (ResourceParseException | IOException e) { throw new ProcessingException(e); } - - return thePolygon; } - private static VdypSpecies getPrimarySpecies(VdypPolygon polygon, Collection speciesList) throws ProcessingException { - + private static VdypSpecies getPrimarySpecies(VdypPolygon polygon, Collection speciesList) + throws ProcessingException { + var primarySpecies = speciesList.stream().filter(s -> s.getSite().isPresent()).toList(); if (primarySpecies.size() == 0) { - throw new ProcessingException(MessageFormat.format("Primary layer of {0} does not contain a primary species", - polygon.getPolygonIdentifier().toStringCompact())); + throw new ProcessingException( + MessageFormat.format( + "Primary layer of {0} does not contain a primary species", + polygon.getPolygonIdentifier().toStringCompact() + ) + ); } else if (primarySpecies.size() > 1) { - throw new ProcessingException(MessageFormat.format("Primary layer of {0} contains multiple primary species: {1}", - polygon.getPolygonIdentifier().toStringCompact(), - String.join(", ", primarySpecies.stream().map(s -> s.getGenus()).toList()))); + throw new ProcessingException( + MessageFormat.format( + "Primary layer of {0} contains multiple primary species: {1}", + polygon.getPolygonIdentifier().toStringCompact(), + String.join(", ", primarySpecies.stream().map(s -> s.getGenus()).toList()) + ) + ); } - + return primarySpecies.get(0); } diff --git a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessingEngine.java b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessingEngine.java index 8232b87e9..fdfdc3966 100644 --- a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessingEngine.java +++ b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessingEngine.java @@ -39,6 +39,7 @@ import ca.bc.gov.nrs.vdyp.forward.model.ControlVariable; import ca.bc.gov.nrs.vdyp.forward.model.ForwardControlVariables; import ca.bc.gov.nrs.vdyp.forward.model.ForwardDebugSettings; +import ca.bc.gov.nrs.vdyp.forward.model.ForwardDebugSettings.Vars; import ca.bc.gov.nrs.vdyp.io.parse.coe.UpperBoundsParser; import ca.bc.gov.nrs.vdyp.io.write.VdypOutputWriter; import ca.bc.gov.nrs.vdyp.math.FloatMath; @@ -88,14 +89,14 @@ public class ForwardProcessingEngine { /** The entity to which result information is written */ private Optional outputWriter = Optional.empty(); - + private final boolean doCheckpoint; public ForwardProcessingEngine(Map controlMap, Optional outputWriter) throws ProcessingException { this.fps = new ForwardProcessingState(controlMap); this.outputWriter = outputWriter; - + int cv7Value = this.fps.fcm.getForwardControlVariables().getControlVariable(ControlVariable.CHECKPOINT_7); doCheckpoint = cv7Value == 1; } @@ -196,10 +197,10 @@ public void processPolygon(VdypPolygon polygon, ExecutionStep lastStepInclusive) logger.info("Starting processing of the primary layer of polygon {}", polygon.getPolygonIdentifier()); - fps.setPolygonLayer(polygon, LayerType.PRIMARY); + fps.setPolygon(polygon); // All of BANKCHK1 that we need. Note that setting UC ALL (METH_CHK == 1) in BANKCHK1 is - // performed when the Bank instance is created in setPolygonLayer, above. + // performed when the Bank instance is created in setPolygon, above. validatePolygon(polygon); @@ -233,28 +234,28 @@ public void processPolygon(VdypPolygon polygon, ExecutionStep lastStepInclusive) private void executeForwardAlgorithm(ExecutionStep lastStepInclusive, int stoppingYearInclusive) throws ProcessingException { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState plps = fps.getPrimaryLayerProcessingState(); - Optional veteranLayer; - if (lps.getPolygon().getLayers().containsKey(LayerType.VETERAN)) { - veteranLayer = Optional.of(lps.getPolygon().getLayers().get(LayerType.VETERAN)); - } else { - veteranLayer = Optional.empty(); - } + Optional veteranLayer = Optional + .ofNullable(fps.getCurrentPolygon().getLayers().get(LayerType.VETERAN)); - // BANKCHK1, simplified for the parameters METH_IN = 4, LayerI = 1, and INSTANCE = 1 if (lastStepInclusive.ge(ExecutionStep.CHECK_FOR_WORK)) { - stopIfNoWork(lps); + stopIfNoWork(fps); } - // SCINXSET - note these are calculated directly from the Primary bank of instance 1 + // SCINXSET if (lastStepInclusive.ge(ExecutionStep.CALCULATE_MISSING_SITE_CURVES)) { - calculateMissingSiteCurves(lps, fps.fcm.getSiteCurveMap()); + calculateMissingSiteCurves(plps, fps.fcm.getSiteCurveMap()); + + fps.getVeteranLayerProcessingState().ifPresent(vlps -> { + assert veteranLayer.isPresent(); + calculateMissingSiteCurves(vlps, fps.fcm.getSiteCurveMap()); + }); } // VPRIME1, method == 1 if (lastStepInclusive.ge(ExecutionStep.CALCULATE_COVERAGES)) { - calculateCoverages(lps); + calculateCoverages(plps); } if (lastStepInclusive.ge(ExecutionStep.DETERMINE_POLYGON_RANKINGS)) { @@ -263,16 +264,16 @@ private void executeForwardAlgorithm(ExecutionStep lastStepInclusive, int stoppi // SITEADD (TODO: SITEADDU when NDEBUG 11 > 0) if (lastStepInclusive.ge(ExecutionStep.ESTIMATE_MISSING_SITE_INDICES)) { - estimateMissingSiteIndices(lps); + estimateMissingSiteIndices(plps); } if (lastStepInclusive.ge(ExecutionStep.ESTIMATE_MISSING_YEARS_TO_BREAST_HEIGHT_VALUES)) { - estimateMissingYearsToBreastHeightValues(lps); + estimateMissingYearsToBreastHeightValues(plps); } // VHDOM1 METH_H = 2, METH_A = 2, METH_SI = 2 if (lastStepInclusive.ge(ExecutionStep.CALCULATE_DOMINANT_HEIGHT_AGE_SITE_INDEX)) { - calculateDominantHeightAgeSiteIndex(lps, fps.fcm.getHl1Coefficients()); + calculateDominantHeightAgeSiteIndex(plps, fps.fcm.getHl1Coefficients()); } // CVSET1 @@ -282,16 +283,12 @@ private void executeForwardAlgorithm(ExecutionStep lastStepInclusive, int stoppi // VGROW1 if (lastStepInclusive.gt(ExecutionStep.SET_COMPATIBILITY_VARIABLES)) { - int startingYear = lps.getPolygon().getPolygonIdentifier().getYear(); - - VdypPolygon vdypPolygon = lps.getPolygon(); - - writePolygon(vdypPolygon, startingYear, startingYear, stoppingYearInclusive); + int startingYear = fps.getCurrentStartingYear(); - Map polygonLayers = vdypPolygon.getLayers(); + writeCurrentPolygon(startingYear, startingYear, stoppingYearInclusive); boolean doRecalculateGroupsPriorToOutput = fps.fcm.getDebugSettings() - .getValue(ForwardDebugSettings.Vars.SPECIES_DYNAMICS_1) != 1 && lps.getNSpecies() > 1; + .getValue(ForwardDebugSettings.Vars.SPECIES_DYNAMICS_1) != 1 && plps.getNSpecies() > 1; boolean doRecalculateGroups = fps.fcm.getForwardControlVariables() .getControlVariable(ControlVariable.UPDATE_DURING_GROWTH_6) >= 1; @@ -300,14 +297,13 @@ private void executeForwardAlgorithm(ExecutionStep lastStepInclusive, int stoppi while (currentYear <= stoppingYearInclusive) { logger.info( - "Growing polygon {} Primary layer for year {}", - lps.getPolygon().getPolygonIdentifier().toStringCompact(), currentYear + "Growing polygon {} Primary layer for year {}", fps.getCompactPolygonIdentifier(), currentYear ); - grow(lps, currentYear, veteranLayer, lastStepInclusive); + grow(plps, currentYear, veteranLayer, lastStepInclusive); // Some unit tests require only some of the grow steps to be executed (and, by - // implication, only for the first growth year. If this is the case, stop + // implication, only for the first growth year.) If this is the case, stop // processing now. if (ExecutionStep.ALL.gt(lastStepInclusive)) { break; @@ -315,23 +311,18 @@ private void executeForwardAlgorithm(ExecutionStep lastStepInclusive, int stoppi // If update-during-growth is set, update the context prior to output if (doRecalculateGroupsPriorToOutput) { - calculateCoverages(lps); - calculateDominantHeightAgeSiteIndex(lps, fps.fcm.getHl1Coefficients()); + calculateCoverages(plps); + calculateDominantHeightAgeSiteIndex(plps, fps.fcm.getHl1Coefficients()); } - VdypLayer updatedLayer = lps.getLayer(); - polygonLayers.put(LayerType.PRIMARY, updatedLayer); - - logger.atInfo().addArgument(updatedLayer.getBaseAreaByUtilization().toString()).log("{}"); - - // Store polygon (both primary and veteran layers) to output - writePolygon(vdypPolygon, startingYear, currentYear, stoppingYearInclusive); + // Write polygon (both primary and veteran layers) to output + writeCurrentPolygon(startingYear, currentYear, stoppingYearInclusive); // If update-during-growth is set, and not already recalculated, recalculate // context now. if (!doRecalculateGroupsPriorToOutput && doRecalculateGroups) { - calculateCoverages(lps); - calculateDominantHeightAgeSiteIndex(lps, fps.fcm.getHl1Coefficients()); + calculateCoverages(plps); + calculateDominantHeightAgeSiteIndex(plps, fps.fcm.getHl1Coefficients()); } currentYear += 1; @@ -358,7 +349,6 @@ private void grow( assert lastStepInclusive.ge(ExecutionStep.GROW_1_LAYER_DHDELTA); Bank bank = lps.getBank(); - VdypPolygon polygon = lps.getPolygon(); float dhStart = lps.getPrimarySpeciesDominantHeight(); int pspSiteCurveNumber = lps.getSiteCurveNumber(lps.getPrimarySpeciesIndex()); @@ -370,7 +360,7 @@ private void grow( float dhDelta = calculateDominantHeightDelta(dhStart, pspSiteCurveNumber, pspSiteIndex, pspYtbhStart); - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_1_LAYER_DHDELTA.eq(lastStepInclusive)) return; @@ -387,7 +377,7 @@ private void grow( float baDelta = calculateBasalAreaDelta(pspYabhStart, dhStart, baStart, veteranLayerBasalArea, dhDelta); - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_2_LAYER_BADELTA.eq(lastStepInclusive)) return; @@ -400,6 +390,11 @@ private void grow( wasDqGrowthLimitApplied ); + writeCheckpoint(currentYear); + + if (ExecutionStep.GROW_3_LAYER_DQDELTA.eq(lastStepInclusive)) + return; + int debugSetting9Value = fps.fcm.getDebugSettings() .getValue(ForwardDebugSettings.Vars.DO_LIMIT_BA_WHEN_DQ_LIMITED_9); if (debugSetting9Value == 1 && wasDqGrowthLimitApplied.get() /* is true */) { @@ -411,11 +406,6 @@ private void grow( float baChangeRate = baDelta / baStart; - writeCheckpoint(polygon, currentYear); - - if (ExecutionStep.GROW_3_LAYER_DQDELTA.eq(lastStepInclusive)) - return; - // (4) Begin storing computed results - dq, ba and tph for the layer // Cache some values for calculations below. @@ -433,7 +423,7 @@ private void grow( bank.basalAreas[0][UC_ALL_INDEX] = baEnd; bank.treesPerHectare[0][UC_ALL_INDEX] = tphEnd; - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_4_LAYER_BA_AND_DQTPH_EST.eq(lastStepInclusive)) return; @@ -478,7 +468,7 @@ private void grow( bank.loreyHeights[0][UC_ALL_INDEX] = sum1 / sum2; - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_5A_LH_EST.eq(lastStepInclusive)) return; @@ -512,7 +502,7 @@ private void grow( } } - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_5_SPECIES_BADQTPH.eq(lastStepInclusive)) return; @@ -529,15 +519,15 @@ private void grow( if (tphEndSum < 0.0f) { throw new ProcessingException( MessageFormat.format( - "During processing of {0}, trees-per-hectare was calculated to be negative ({1})", - lps.getPolygon().getLayers().get(LayerType.PRIMARY), tphEndSum + "During processing of primary layer of {0}, trees-per-hectare was calculated to be negative ({1})", + fps.getCompactPolygonIdentifier(), tphEndSum ) ); } bank.treesPerHectare[0][UC_ALL_INDEX] = tphEndSum; - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_6_LAYER_TPH2.eq(lastStepInclusive)) return; @@ -547,7 +537,7 @@ private void grow( bank.quadMeanDiameters[0][UC_ALL_INDEX] = BaseAreaTreeDensityDiameter .quadMeanDiameter(bank.basalAreas[0][UC_ALL_INDEX], bank.treesPerHectare[0][UC_ALL_INDEX]); - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_7_LAYER_DQ2.eq(lastStepInclusive)) return; @@ -560,7 +550,7 @@ private void grow( // We now have site (layer) level predications for basal area, quad-mean-diameter, // trees-per-hectare and Lorey height. Proceed to per-species estimates. - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_8_SPECIES_LH.eq(lastStepInclusive)) return; @@ -571,7 +561,7 @@ private void grow( / bank.basalAreas[0][UC_ALL_INDEX]; } - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_9_SPECIES_PCT.eq(lastStepInclusive)) return; @@ -579,7 +569,7 @@ private void grow( // (10) Update the running values. lps.updatePrimarySpeciesDetailsAfterGrowth(dhEnd); - for (int i = 1; i < bank.getNSpecies(); i++) { + for (int i : lps.getIndices()) { if (i == lps.getPrimarySpeciesIndex()) { bank.ageTotals[i] = lps.getPrimarySpeciesTotalAge(); bank.dominantHeights[i] = dhEnd; @@ -611,7 +601,12 @@ private void grow( } } - writeCheckpoint(polygon, currentYear); + fps.getVeteranLayerProcessingState().ifPresent(vlps -> { + assert veteranLayer.isPresent(); + updateVeteranSpeciesAges(vlps); + }); + + writeCheckpoint(currentYear); if (ExecutionStep.GROW_10_STORE_SPECIES_DETAILS.eq(lastStepInclusive)) return; @@ -619,14 +614,14 @@ private void grow( // (11) update the compatibility variables to reflect the changes during the growth period lps.updateCompatibilityVariablesAfterGrowth(); - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_11_COMPATIBILITY_VARS.eq(lastStepInclusive)) return; // (12) calculate All and the large component volumes to reflect the changes in growth - VdypLayer primaryLayer = lps.getLayer(); + VdypLayer primaryLayer = fps.updatePolygon().getLayers().get(LayerType.PRIMARY); VolumeComputeMode volumeComputationMode = VolumeComputeMode.BY_UTIL_WITH_WHOLE_STEM_BY_SPEC; int controlVariable3Value = fps.fcm.getForwardControlVariables() @@ -639,7 +634,7 @@ private void grow( bank.refreshBank(primaryLayer); - writeCheckpoint(polygon, currentYear); + writeCheckpoint(currentYear); if (ExecutionStep.GROW_12_SPECIES_UC.eq(lastStepInclusive)) return; @@ -648,14 +643,26 @@ private void grow( calculateSmallComponentYields(lps); + writeCheckpoint(currentYear); + if (ExecutionStep.GROW_13_SPECIES_UC_SMALL.eq(lastStepInclusive)) return; } - - private void writeCheckpoint(VdypPolygon polygon, int year) { + + private void updateVeteranSpeciesAges(LayerProcessingState vlps) { + + for (int i : vlps.getIndices()) { + vlps.getBank().ageTotals[i] += 1; + vlps.getBank().yearsAtBreastHeight[i] += 1; + } + + } + + private void writeCheckpoint(int year) { if (doCheckpoint) { outputWriter.ifPresent(o -> { try { + var polygon = fps.updatePolygon(); o.writePolygonWithSpeciesAndUtilizationForYear(polygon, year); } catch (IOException e) { throw new RuntimeProcessingException(new ProcessingException(e)); @@ -675,7 +682,7 @@ private void writeCheckpoint(VdypPolygon polygon, int year) { */ void growUsingNoSpeciesDynamics(float baChangeRate, float tphChangeRate) { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); Bank bank = lps.getBank(); for (int i : lps.getIndices()) { @@ -745,10 +752,9 @@ boolean growUsingPartialSpeciesDynamics( float baStart, float baDelta, float dqStart, float dqDelta, float tphStart, float[] lhAtStart ) throws ProcessingException { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); Bank bank = lps.getBank(); - VdypPolygon polygon = lps.getPolygon(); - Region polygonRegion = polygon.getBiogeoclimaticZone().getRegion(); + Region polygonRegion = fps.getCurrentBecZone().getRegion(); if (dqDelta == 0 || baDelta == 0 || lps.getNSpecies() == 1) { return false /* no solution available */; @@ -984,7 +990,7 @@ boolean growUsingPartialSpeciesDynamics( "Polygon {0}, layer {1}: while computing growth" + " using partial species dynamics, trees-per-hectare lower bound ({2}) was found to be" + " greater than the upper bound ({3})", - polygon.getPolygonIdentifier().toStringCompact(), lps.getLayerType(), tphLow, tphHigh + fps.getCompactPolygonIdentifier(), lps.getLayerType(), tphLow, tphHigh ) ); } @@ -1044,7 +1050,7 @@ void growUsingFullSpeciesDynamics( float baStart, float baDelta, float dqStart, float dqDelta, float tphStart, float lhStart ) throws ProcessingException { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); Bank bank = lps.getBank(); float spBaEnd[] = new float[lps.getNSpecies() + 1]; @@ -1281,7 +1287,7 @@ private float calculateQuadMeanDiameterDeltaForPrimarySpecies( float dqStart, float dqDelta, float pspDqStart, float lhStart, float pspLhStart ) throws ProcessingException { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); int pspStratumNumber = lps.getPrimarySpeciesStratumNumber(); ModelCoefficients mc = fps.fcm.getPrimarySpeciesQuadMeanDiameterGrowthCoefficients().get(pspStratumNumber); @@ -1316,7 +1322,7 @@ private float calculateQuadMeanDiameterDeltaForNonPrimarySpecies( int speciesIndex, float dqStart, float dqDelta, float spDqStart, float lhStart, float spLhStart ) throws ProcessingException { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); String speciesName = lps.getBank().speciesNames[speciesIndex]; int pspStratumNumber = lps.getPrimarySpeciesStratumNumber(); @@ -1399,7 +1405,7 @@ private float growBasalAreaForNonPrimarySpecies( float spLhStart ) throws ProcessingException { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); if (spBaStart <= 0.0f || spBaStart >= baStart) { throw new ProcessingException( @@ -1465,7 +1471,7 @@ private float growBasalAreaForPrimarySpecies( float baStart, float baDelta, float pspBaStart, float dhStart, float pspYabhStart, float pspLhStart ) throws ProcessingException { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); float pspBaDelta; @@ -1532,7 +1538,7 @@ private void calculateSmallComponentYields(LayerProcessingState lps) throws Proc float smallProbability = smallComponentProbability(speciesName, spLhAll, region); // This whole operation is on Actual BA's, not 100% occupancy. - float fractionAvailable = lps.getPolygon().getPercentAvailable() / 100.0f; + float fractionAvailable = fps.getCurrentPolygon().getPercentAvailable() / 100.0f; if (fractionAvailable > 0.0f) { spBaAll *= fractionAvailable; @@ -1638,7 +1644,7 @@ void growLoreyHeights( int debugSetting8Value = fps.fcm.getDebugSettings() .getValue(ForwardDebugSettings.Vars.LOREY_HEIGHT_CHANGE_STRATEGY_8); - int primarySpeciesIndex = fps.getLayerProcessingState().getPrimarySpeciesIndex(); + int primarySpeciesIndex = fps.getPrimaryLayerProcessingState().getPrimarySpeciesIndex(); if (debugSetting8Value != 2 || dhStart != dhEnd) { bank.loreyHeights[primarySpeciesIndex][UC_ALL_INDEX] = pspLhEnd; } else if (debugSetting8Value == 2) { @@ -1672,8 +1678,8 @@ void growLoreyHeights( */ private float estimatePrimarySpeciesLoreyHeight(float dh, float pspTph) { - String primarySpeciesAlias = fps.getLayerProcessingState().getPrimarySpeciesAlias(); - Region polygonRegion = fps.getLayerProcessingState().getBecZone().getRegion(); + String primarySpeciesAlias = fps.getPrimaryLayerProcessingState().getPrimarySpeciesAlias(); + Region polygonRegion = fps.getPrimaryLayerProcessingState().getBecZone().getRegion(); var coefficients = fps.fcm.getLoreyHeightPrimarySpeciesEquationP1Coefficients(); float a0 = coefficients.get(primarySpeciesAlias, polygonRegion).getCoe(1); @@ -1695,7 +1701,7 @@ private float estimatePrimarySpeciesLoreyHeight(float dh, float pspTph) { * @return as described */ private float estimateNonPrimarySpeciesLoreyHeight(int speciesIndex, float dh, float pspLoreyHeight) { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); Bank bank = lps.getBank(); float spLh; @@ -1747,7 +1753,7 @@ float calculateQuadMeanDiameterDelta( Optional veteranBaEnd, float dhDelta, Reference dqGrowthLimitApplied ) throws StandProcessingException { - var lps = fps.getLayerProcessingState(); + var lps = fps.getPrimaryLayerProcessingState(); var becZone = lps.getBecZone(); float[] speciesProportionsByBasalArea = getSpeciesProportionsByBasalAreaAtStartOfYear(); @@ -1768,11 +1774,10 @@ float calculateQuadMeanDiameterDelta( float dqUpperBound = growQuadraticMeanDiameterUpperBound(); float dqLimit = Math.max(dqUpperBound, dqStart); - int controlVariable2Value = fps.fcm.getForwardControlVariables() - .getControlVariable(ControlVariable.COMPAT_VAR_OUTPUT_2); + int debugVariable2Value = fps.fcm.getDebugSettings().getValue(Vars.MAX_BREAST_HEIGHT_AGE_2); float dqYieldStart = fps.estimators.estimateQuadMeanDiameterYield( - coefficientsWeightedBySpeciesAndDecayBec, controlVariable2Value, dhStart, pspYabhStart, veteranBaStart, + coefficientsWeightedBySpeciesAndDecayBec, debugVariable2Value, dhStart, pspYabhStart, veteranBaStart, dqLimit ); @@ -1780,8 +1785,7 @@ float calculateQuadMeanDiameterDelta( float pspYabhEnd = pspYabhStart + 1.0f; float dqYieldEnd = fps.estimators.estimateQuadMeanDiameterYield( - coefficientsWeightedBySpeciesAndDecayBec, controlVariable2Value, dhEnd, pspYabhEnd, veteranBaEnd, - dqLimit + coefficientsWeightedBySpeciesAndDecayBec, debugVariable2Value, dhEnd, pspYabhEnd, veteranBaEnd, dqLimit ); float dqYieldGrowth = dqYieldEnd - dqYieldStart; @@ -1873,7 +1877,7 @@ private float calculateQuadMeanDiameterGrowthEmpirical( var dqGrowthEmpiricalCoefficients = fps.fcm.getQuadMeanDiameterGrowthEmpiricalCoefficients(); - Integer stratumNumber = fps.getLayerProcessingState().getPrimarySpeciesStratumNumber(); + Integer stratumNumber = fps.getPrimaryLayerProcessingState().getPrimarySpeciesStratumNumber(); var firstSpeciesDqGrowthCoe = dqGrowthEmpiricalCoefficients.get(stratumNumber); float a0 = firstSpeciesDqGrowthCoe.get(0); @@ -1922,12 +1926,12 @@ private float calculateQuadMeanDiameterGrowthEmpirical( */ private float[] getSpeciesProportionsByBasalAreaAtStartOfYear() { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); Bank bank = lps.getBank(); float[] speciesProportionsByBasalArea = new float[lps.getNSpecies() + 1]; - for (int i = 1; i <= lps.getNSpecies(); i++) { + for (int i : lps.getIndices()) { speciesProportionsByBasalArea[i] = bank.basalAreas[i][UC_ALL_INDEX] / bank.basalAreas[0][UC_ALL_INDEX]; } @@ -1951,13 +1955,13 @@ float calculateBasalAreaDelta( ) throws StandProcessingException { ForwardDebugSettings debugSettings = fps.fcm.getDebugSettings(); - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); Bank bank = lps.getBank(); float[] speciesProportionsByBasalArea = getSpeciesProportionsByBasalAreaAtStartOfYear(); var baYieldCoefficients = fps.fcm.getBasalAreaYieldCoefficients(); - var becZoneAlias = fps.getLayerProcessingState().getBecZone().getAlias(); + var becZoneAlias = fps.getPrimaryLayerProcessingState().getBecZone().getAlias(); Coefficients estimateBasalAreaYieldCoefficients = Coefficients.empty(7, 0); for (int i = 0; i <= 6; i++) { float sum = 0.0f; @@ -1993,7 +1997,7 @@ float calculateBasalAreaDelta( ); var growthFaitDetails = fps.fcm.getBasalAreaGrowthFiatDetails() - .get(fps.getLayerProcessingState().getBecZone().getRegion()); + .get(fps.getPrimaryLayerProcessingState().getBecZone().getRegion()); var convergenceCoefficient = growthFaitDetails.calculateCoefficient(pspYabhStart); @@ -2074,7 +2078,7 @@ private float calculateBasalAreaGrowthEmpirical( var basalAreaGrowthEmpiricalCoefficients = fps.fcm.getBasalAreaGrowthEmpiricalCoefficients(); - String becZoneAlias = fps.getLayerProcessingState().getBecZone().getAlias(); + String becZoneAlias = fps.getPrimaryLayerProcessingState().getBecZone().getAlias(); String firstSpecies = fps.fcm.getGenusDefinitionMap().getByIndex(1).getAlias(); var firstSpeciesBaGrowthCoe = basalAreaGrowthEmpiricalCoefficients.get(becZoneAlias, firstSpecies); @@ -2087,8 +2091,8 @@ private float calculateBasalAreaGrowthEmpirical( float b6 = firstSpeciesBaGrowthCoe.get(6); float b7 = firstSpeciesBaGrowthCoe.get(7); - for (int i = 1; i <= fps.getLayerProcessingState().getNSpecies(); i++) { - String speciesAlias = fps.getLayerProcessingState().getBank().speciesNames[i]; + for (int i = 1; i <= fps.getPrimaryLayerProcessingState().getNSpecies(); i++) { + String speciesAlias = fps.getPrimaryLayerProcessingState().getBank().speciesNames[i]; var baGrowthCoe = basalAreaGrowthEmpiricalCoefficients.get(becZoneAlias, speciesAlias); b4 += speciesBasalAreaProportions[i] * baGrowthCoe.getCoe(4); b5 += speciesBasalAreaProportions[i] * baGrowthCoe.getCoe(5); @@ -2133,7 +2137,7 @@ private float calculateBasalAreaGrowthEmpirical( */ private float growBasalAreaUpperBound() { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); int debugSetting4Value = fps.fcm.getDebugSettings() .getValue(ForwardDebugSettings.Vars.PER_SPECIES_AND_REGION_MAX_BREAST_HEIGHT_4); @@ -2153,7 +2157,7 @@ private float growBasalAreaUpperBound() { */ private float growQuadraticMeanDiameterUpperBound() { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); int debugSetting4Value = fps.fcm.getDebugSettings() .getValue(ForwardDebugSettings.Vars.PER_SPECIES_AND_REGION_MAX_BREAST_HEIGHT_4); @@ -2164,7 +2168,7 @@ private float growQuadraticMeanDiameterUpperBound() { int primarySpeciesIndex = lps.getPrimarySpeciesIndex(); return upperBoundsCoefficients.get(region, lps.getBank().speciesNames[primarySpeciesIndex], 2); } else { - var primarySpeciesGroupNumber = fps.getLayerProcessingState().getPrimarySpeciesGroupNumber(); + var primarySpeciesGroupNumber = fps.getPrimaryLayerProcessingState().getPrimarySpeciesGroupNumber(); return fps.fcm.getUpperBounds().get(primarySpeciesGroupNumber).getCoe(UpperBoundsParser.DQ_INDEX); } } @@ -2185,7 +2189,7 @@ float calculateDominantHeightDelta(float spDhStart, int siteCurveNumber, float s throws ProcessingException { SiteCurveAgeMaximum scAgeMaximums = fps.fcm.getMaximumAgeBySiteCurveNumber().get(siteCurveNumber); - Region region = fps.getLayerProcessingState().getBank().getBecZone().getRegion(); + Region region = fps.getPrimaryLayerProcessingState().getBank().getBecZone().getRegion(); if (siteCurveNumber == VdypEntity.MISSING_INTEGER_VALUE) { throw new ProcessingException("No SiteCurveNumber supplied"); @@ -2367,11 +2371,12 @@ private static double ageAndSiteIndexToHeight( } } - private void writePolygon(VdypPolygon polygon, int startYear, int currentYear, int endYear) - throws ProcessingException { + private void writeCurrentPolygon(int startYear, int currentYear, int endYear) throws ProcessingException { try { outputWriter.ifPresent((o) -> { + var polygon = fps.updatePolygon(); + logger.info("Writing polygon {} for year {}", polygon, currentYear); int controlVariable4Value = fps.fcm.getForwardControlVariables() @@ -2422,7 +2427,7 @@ private void writePolygon(VdypPolygon polygon, int startYear, int currentYear, i throw e.getCause(); } } - + private static final float[] DEFAULT_QUAD_MEAN_DIAMETERS = new float[] { Float.NaN, 10.0f, 15.0f, 20.0f, 25.0f }; private static final float V_BASE_MIN = 0.1f; private static final float B_BASE_MIN = 0.01f; @@ -2439,7 +2444,7 @@ void setCompatibilityVariables() throws ProcessingException { Coefficients aAdjust = new Coefficients(new float[] { 0.0f, 0.0f, 0.0f, 0.0f }, 1); var growthDetails = fps.fcm.getForwardControlVariables(); - var lps = fps.getLayerProcessingState(); + var lps = fps.getPrimaryLayerProcessingState(); Bank bank = lps.getBank(); // Note: L1COM2 (INL1VGRP, INL1DGRP, INL1BGRP) is initialized when @@ -2456,7 +2461,6 @@ void setCompatibilityVariables() throws ProcessingException { var cvQuadraticMeanDiameter = new MatrixMap2[lps.getNSpecies() + 1]; var cvSmall = new HashMap[lps.getNSpecies() + 1]; - System.out.println("Polygon: " + lps.getPolygon()); for (int s : lps.getIndices()) { String genusName = bank.speciesNames[s]; @@ -2643,7 +2647,7 @@ void setCompatibilityVariables() throws ProcessingException { calculateSmallCompatibilityVariables(int speciesIndex, ForwardControlVariables forwardControlVariables) throws ProcessingException { - var lps = fps.getLayerProcessingState(); + var lps = fps.getPrimaryLayerProcessingState(); Bank bank = lps.getBank(); Region region = lps.getBecZone().getRegion(); @@ -2724,7 +2728,7 @@ void setCompatibilityVariables() throws ProcessingException { * @return as described */ private float smallComponentProbability(String speciesAlias, float loreyHeight, Region region) { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); Coefficients coe = fps.fcm.getSmallComponentProbabilityCoefficients().get(speciesAlias); @@ -3135,7 +3139,12 @@ static void estimateMissingSiteIndices(LayerProcessingState lps) throws Processi try { double mappedSiteIndex = SiteTool .convertSiteIndexBetweenCurves(pspSiteCurve, pspSiteIndex, spSiteCurve); - bank.siteIndices[spIndex] = (float) mappedSiteIndex; + if (mappedSiteIndex > 1.3f) { + pspSiteIndex = (float) mappedSiteIndex; + } + if (mappedSiteIndex > 0.0f) { + bank.siteIndices[spIndex] = (float) mappedSiteIndex; + } } catch (NoAnswerException e) { logger.warn( MessageFormat.format( @@ -3258,7 +3267,7 @@ private static void validatePolygon(VdypPolygon polygon) throws ProcessingExcept } } - private static void stopIfNoWork(LayerProcessingState lps) throws ProcessingException { + private static void stopIfNoWork(ForwardProcessingState fps) throws ProcessingException { // The following is extracted from BANKCHK1, simplified for the parameters // METH_IN = 4, LayerI = 1, and INSTANCE = 1. So IR = 1, which is the first @@ -3267,11 +3276,11 @@ private static void stopIfNoWork(LayerProcessingState lps) throws ProcessingExce // => all that is done is that an exception is thrown if there are no species to // process. - if (lps.getNSpecies() == 0) { + if (fps.getPrimaryLayerProcessingState().getNSpecies() == 0) { throw new ProcessingException( MessageFormat.format( "Polygon {0} layer 0 has no species with basal area above {1}", - lps.getPolygon().getPolygonIdentifier().toStringCompact(), MIN_BASAL_AREA + fps.getCompactPolygonIdentifier(), MIN_BASAL_AREA ) ); } @@ -3296,7 +3305,7 @@ private static void stopIfNoWork(LayerProcessingState lps) throws ProcessingExce */ void determinePolygonRankings(Collection> speciesToCombine) { - LayerProcessingState lps = fps.getLayerProcessingState(); + LayerProcessingState lps = fps.getPrimaryLayerProcessingState(); Bank bank = lps.getBank(); if (lps.getNSpecies() == 0) { diff --git a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessingState.java b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessingState.java index a9475a840..95b3b2538 100644 --- a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessingState.java +++ b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessingState.java @@ -1,6 +1,7 @@ package ca.bc.gov.nrs.vdyp.forward; import java.util.Map; +import java.util.Optional; import ca.bc.gov.nrs.vdyp.application.ProcessingException; import ca.bc.gov.nrs.vdyp.application.VdypApplicationIdentifier; @@ -8,6 +9,7 @@ import ca.bc.gov.nrs.vdyp.common.EstimationMethods; import ca.bc.gov.nrs.vdyp.forward.controlmap.ForwardResolvedControlMap; import ca.bc.gov.nrs.vdyp.forward.controlmap.ForwardResolvedControlMapImpl; +import ca.bc.gov.nrs.vdyp.model.BecDefinition; import ca.bc.gov.nrs.vdyp.model.LayerType; import ca.bc.gov.nrs.vdyp.model.VdypPolygon; @@ -22,8 +24,14 @@ public class ForwardProcessingState { /** The computation instance used by this engine */ final ComputationMethods computers; - /** The active state */ - private LayerProcessingState lps; + /** The polygon on which the Processor is currently operating */ + private VdypPolygon polygon; + + /** The processing state of the primary layer of polygon */ + private LayerProcessingState plps; + + /** The processing state of the veteran layer of polygon */ + private Optional vlps; public ForwardProcessingState(Map controlMap) throws ProcessingException { this.fcm = new ForwardResolvedControlMapImpl(controlMap); @@ -31,12 +39,51 @@ public ForwardProcessingState(Map controlMap) throws ProcessingE this.computers = new ComputationMethods(estimators, VdypApplicationIdentifier.VDYP_FORWARD); } - public void setPolygonLayer(VdypPolygon polygon, LayerType subjectLayer) throws ProcessingException { + public void setPolygon(VdypPolygon polygon) throws ProcessingException { + + this.polygon = polygon; + + this.plps = new LayerProcessingState(this, polygon.getLayers().get(LayerType.PRIMARY)); + if (polygon.getLayers().containsKey(LayerType.VETERAN)) { + this.vlps = Optional.of(new LayerProcessingState(this, polygon.getLayers().get(LayerType.VETERAN))); + } else { + this.vlps = Optional.empty(); + } + } + + /** @return the current polygon */ + public VdypPolygon getCurrentPolygon() { + return polygon; + } + + /** @return the compact form of the current polygon's identifier. Shortcut. */ + public String getCompactPolygonIdentifier() { + return polygon.getPolygonIdentifier().toStringCompact(); + } - lps = new LayerProcessingState(this, polygon, subjectLayer); + /** @return the starting year of the current polygon. Shortcut. */ + public int getCurrentStartingYear() { + return polygon.getPolygonIdentifier().getYear(); } - public LayerProcessingState getLayerProcessingState() { - return lps; + /** @return the bec zone of the current polygon. Shortcut. */ + public BecDefinition getCurrentBecZone() { + return polygon.getBiogeoclimaticZone(); + } + + public LayerProcessingState getPrimaryLayerProcessingState() { + return plps; + } + + public Optional getVeteranLayerProcessingState() { + return vlps; + } + + public VdypPolygon updatePolygon() { + + polygon.getLayers().put(LayerType.PRIMARY, plps.updateLayerFromBank()); + vlps.ifPresent(vlps -> polygon.getLayers().put(LayerType.VETERAN, vlps.updateLayerFromBank())); + + return polygon; } } \ No newline at end of file diff --git a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/LayerProcessingState.java b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/LayerProcessingState.java index 5d0e2fcef..e262a49a2 100644 --- a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/LayerProcessingState.java +++ b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/LayerProcessingState.java @@ -7,7 +7,6 @@ import org.slf4j.Logger; import org.slf4j.LoggerFactory; -import ca.bc.gov.nrs.vdyp.application.ProcessingException; import ca.bc.gov.nrs.vdyp.forward.model.ControlVariable; import ca.bc.gov.nrs.vdyp.model.BecDefinition; import ca.bc.gov.nrs.vdyp.model.LayerType; @@ -17,7 +16,6 @@ import ca.bc.gov.nrs.vdyp.model.UtilizationClassVariable; import ca.bc.gov.nrs.vdyp.model.VdypEntity; import ca.bc.gov.nrs.vdyp.model.VdypLayer; -import ca.bc.gov.nrs.vdyp.model.VdypPolygon; import ca.bc.gov.nrs.vdyp.model.VdypSpecies; import ca.bc.gov.nrs.vdyp.model.VolumeVariable; @@ -42,9 +40,6 @@ class LayerProcessingState { /** The containing ForwardProcessingState */ private final ForwardProcessingState fps; - /** The containing polygon of the layer on which the Processor is operating */ - private final VdypPolygon polygon; - /** The type of Layer being processed */ private final LayerType layerType; @@ -115,17 +110,13 @@ class LayerProcessingState { // MNSP - MSPL1, MSPLV // TODO - public LayerProcessingState(ForwardProcessingState fps, VdypPolygon polygon, LayerType subjectLayerType) - throws ProcessingException { + public LayerProcessingState(ForwardProcessingState fps, VdypLayer layer) { this.fps = fps; - this.polygon = polygon; - this.layerType = subjectLayerType; - - BecDefinition becZone = polygon.getBiogeoclimaticZone(); + this.layerType = layer.getLayerType(); bank = new Bank( - polygon.getLayers().get(subjectLayerType), becZone, + layer, fps.getCurrentBecZone(), s -> s.getBaseAreaByUtilization().get(UtilizationClass.ALL) >= ForwardProcessingEngine.MIN_BASAL_AREA ); @@ -154,10 +145,6 @@ public LayerProcessingState(ForwardProcessingState fps, VdypPolygon polygon, Lay } } - public VdypPolygon getPolygon() { - return polygon; - } - public LayerType getLayerType() { return layerType; } @@ -381,8 +368,8 @@ public void setPrimarySpeciesDetails(PrimarySpeciesDetails details) { public void updatePrimarySpeciesDetailsAfterGrowth(float newPrimarySpeciesDominantHeight) { this.primarySpeciesDominantHeight = newPrimarySpeciesDominantHeight; - primarySpeciesTotalAge += 1; - primarySpeciesAgeAtBreastHeight += 1; + this.primarySpeciesTotalAge += 1; + this.primarySpeciesAgeAtBreastHeight += 1; // primarySpeciesSiteIndex - does this change? // primarySpeciesAgeToBreastHeight of course doesn't change. @@ -475,15 +462,19 @@ public float getCVSmall(int speciesIndex, UtilizationClassVariable variable) { return cvPrimaryLayerSmall[speciesIndex].get(variable); } - public VdypLayer getLayer() { + VdypLayer updateLayerFromBank() { - VdypLayer updatedLayer = bank.getLayer(); + VdypLayer updatedLayer = bank.buildLayerFromBank(); - for (int i = 1; i < getNSpecies() + 1; i++) { - VdypSpecies species = updatedLayer.getSpeciesBySp0(bank.speciesNames[i]); - species.setCompatibilityVariables( - cvVolume[i], cvBasalArea[i], cvQuadraticMeanDiameter[i], cvPrimaryLayerSmall[i] - ); + if (layerType.equals(LayerType.PRIMARY)) { + // Inject the compatibility variable values. + for (int i = 1; i < getNSpecies() + 1; i++) { + VdypSpecies species = updatedLayer.getSpeciesBySp0(bank.speciesNames[i]); + + species.setCompatibilityVariables( + cvVolume[i], cvBasalArea[i], cvQuadraticMeanDiameter[i], cvPrimaryLayerSmall[i] + ); + } } return updatedLayer; diff --git a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/UtilizationOperations.java b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/UtilizationOperations.java index 1320b2c23..9efba0821 100644 --- a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/UtilizationOperations.java +++ b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/UtilizationOperations.java @@ -7,6 +7,7 @@ import ca.bc.gov.nrs.vdyp.application.ProcessingException; import ca.bc.gov.nrs.vdyp.common_calculators.BaseAreaTreeDensityDiameter; import ca.bc.gov.nrs.vdyp.math.FloatMath; +import ca.bc.gov.nrs.vdyp.model.LayerType; import ca.bc.gov.nrs.vdyp.model.UtilizationClass; import ca.bc.gov.nrs.vdyp.model.VdypLayer; import ca.bc.gov.nrs.vdyp.model.VdypPolygon; @@ -19,8 +20,9 @@ public class UtilizationOperations { /** * Perform the following operations on the UtilizationVectors of the given polygon. *

    - *
  1. Scale the per-hectare values of all the utilizations of the primary layer of the given polygon, and - *
  2. For all utilizations of both the primary and veteran layer (if present) of the polygon: + *
  3. (VDYPGETU 212:231) Scale the per-hectare values of all the utilizations of the primary layer of the given + * polygon, and + *
  4. (BANKIN2, ICHECK=2) For all utilizations of both the primary and veteran layer (if present) of the polygon: *
      *
    • Adjust the basal area to be within bounds of the utilization class, and *
    • Calculate the quad-mean-diameter value from the basal area and trees per hectare. @@ -35,6 +37,19 @@ public static void doPostCreateAdjustments(VdypPolygon polygon) throws Processin assert !Float.isNaN(percentForestedLand); float scalingFactor = 100.0f / percentForestedLand; + List primaryLayerUtilizationsToScale = new ArrayList<>(); + + VdypLayer primaryLayer = polygon.getLayers().get(LayerType.PRIMARY); + primaryLayerUtilizationsToScale.add(primaryLayer); + primaryLayer.getSpecies().values().stream().forEach(s -> primaryLayerUtilizationsToScale.add(s)); + + for (VdypUtilizationHolder uh : primaryLayerUtilizationsToScale) { + + if (percentForestedLand > 0.0f && percentForestedLand < 100.0f) { + scale(uh, scalingFactor); + } + } + List utilizationsToAdjust = new ArrayList<>(); for (VdypLayer l : polygon.getLayers().values()) { @@ -46,13 +61,11 @@ public static void doPostCreateAdjustments(VdypPolygon polygon) throws Processin for (VdypUtilizationHolder uh : utilizationsToAdjust) { - if (percentForestedLand > 0.0f && percentForestedLand < 100.0f) { - scale(uh, scalingFactor); - } - // Implements the logic in BANKIN2 (ICHECK == 2) adjusting the utilization values according to various // rules. + // BANKCHK1, simplified for the parameters METH_IN = 4, LayerI = 1, and INSTANCE = 1 + resetOnMissingValues(uh); adjustBasalAreaToMatchTreesPerHectare(uh); @@ -62,8 +75,8 @@ public static void doPostCreateAdjustments(VdypPolygon polygon) throws Processin } /** - * Implements VDYPGETU lines 224 - 229, in which the utilization-per-hectare values are scaled by the given factor - - * the % coverage of the primary layer. + * Implements VDYPGETU lines 212-231, in which the per-hectare utilization values are scaled by the 100 / (% + * forested land of polygon) of the PRIMARY LAYER only. * * @param scalingFactor the factor by which the uh is to be scaled */ diff --git a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/VdypForwardApplication.java b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/VdypForwardApplication.java index 030fea132..d149f83a7 100644 --- a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/VdypForwardApplication.java +++ b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/VdypForwardApplication.java @@ -44,7 +44,6 @@ public class VdypForwardApplication extends VdypApplication { private static Set vdypPassSet = new HashSet<>(Arrays.asList(PASS_1, PASS_2, PASS_3, PASS_4, PASS_5)); - @SuppressWarnings("java:S106") public static void main(final String... args) { var app = new VdypForwardApplication(); diff --git a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/model/ForwardControlVariables.java b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/model/ForwardControlVariables.java index 2bec4b5a0..4f22bb3fa 100644 --- a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/model/ForwardControlVariables.java +++ b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/model/ForwardControlVariables.java @@ -46,9 +46,8 @@ *
    • 0: No *
    • 1: Yes (normal) *
    - * 7th: Checkpoint growth. Polygons are written to the output files after - * each step of the grow process. The final write for a given year is the - * result of growth for that year; the others are all intermediate. + * 7th: Checkpoint growth. Polygons are written to the output files after each step of the grow process. The final write + * for a given year is the result of growth for that year; the others are all intermediate. *
      *
    • 0: No *
    • 1: Yes (normal) diff --git a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/parsers/VdypSpeciesParser.java b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/parsers/VdypSpeciesParser.java index ae0135286..968de8931 100644 --- a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/parsers/VdypSpeciesParser.java +++ b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/parsers/VdypSpeciesParser.java @@ -61,8 +61,7 @@ public ControlKey getControlKey() { map(String fileName, FileResolver fileResolver, Map controlMap) throws IOException, ResourceParseException { return () -> { - var lineParser = new LineParser() - .strippedString(25, DESCRIPTION) // + var lineParser = new LineParser().strippedString(25, DESCRIPTION) // .space(1) // .value( 1, LAYER_TYPE, @@ -72,7 +71,8 @@ public ControlKey getControlKey() { x -> x == null || x.trim().length() == 0 || x.trim().equals("Z"), EndOfRecord.END_OF_RECORD ) - )) // + ) + ) // .space(1) // .value(2, GENUS_INDEX, ValueParser.INTEGER) // .space(1) // @@ -163,7 +163,7 @@ protected ValueOrMarker, EndOfRecord> convert(Map 0.0 && yearsToBreastHeight > 0.0) iTotalAge = yearsAtBreastHeight + yearsToBreastHeight; diff --git a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/parsers/VdypUtilizationParser.java b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/parsers/VdypUtilizationParser.java index c86825eca..a8b10f5a6 100644 --- a/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/parsers/VdypUtilizationParser.java +++ b/lib/vdyp-forward/src/main/java/ca/bc/gov/nrs/vdyp/forward/parsers/VdypUtilizationParser.java @@ -62,8 +62,7 @@ public ControlKey getControlKey() { EndOfRecord.END_OF_RECORD ) ) - ) - .value(3, GENUS_INDEX, ValueParser.INTEGER) // + ).value(3, GENUS_INDEX, ValueParser.INTEGER) // .space(1) // .value(2, GENUS, ControlledValueParser.optional(ValueParser.GENUS)) .value(3, UTILIZATION_CLASS_INDEX, ControlledValueParser.UTILIZATION_CLASS) diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/ForwardControlParserTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/ForwardControlParserTest.java index cf63e3e29..085eb91ce 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/ForwardControlParserTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/ForwardControlParserTest.java @@ -149,7 +149,7 @@ ControlKey.SITE_CURVE_NUMBERS, allOf( @Test void testParseE025Empty() throws Exception { var parser = new ForwardControlParser(); - var result = ForwardTestUtils.parse(parser, "VDYP-NoSiteCurves.CTR"); + var result = ForwardTestUtils.parse(parser, "VDYP.CTR"); assertThat(result, (Matcher) controlMapHasEntry(ControlKey.SITE_CURVE_NUMBERS, mmEmpty())); } diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessorCheckpointGenerationTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessorCheckpointGenerationTest.java index a6aea4931..67fc69238 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessorCheckpointGenerationTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/ForwardProcessorCheckpointGenerationTest.java @@ -39,9 +39,9 @@ void test() throws IOException, ResourceParseException, ProcessingException { FileResolver inputFileResolver = TestUtils.fileResolver(TestUtils.class); - Path vdyp7OutputPath = Path.of(System.getenv().get("HOME"), "tmp", "vdyp7"); + Path vdyp7OutputPath = Path.of(System.getenv().get("HOME"), "tmp", "vdyp-deltas", "vdyp8"); Files.createDirectories(vdyp7OutputPath); - + var outputResolver = new FileSystemFileResolver(vdyp7OutputPath); fp.run(inputFileResolver, outputResolver, List.of("VDYP-Checkpoint.CTR"), vdypPassSet); diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow10StoreSpeciesDetails.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow10StoreSpeciesDetails.java index 5dfb93c03..b5dc2d8a6 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow10StoreSpeciesDetails.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow10StoreSpeciesDetails.java @@ -59,7 +59,7 @@ void testStandardPath() throws ProcessingException, ValueParseException { fpe.processPolygon(polygon, ExecutionStep.GROW_10_STORE_SPECIES_DETAILS); // VDYP7 reports [], -9, -9, 35.473381, -9, -9) - Bank bank = fpe.fps.getLayerProcessingState().getBank(); + Bank bank = fpe.fps.getPrimaryLayerProcessingState().getBank(); assertThat( ForwardTestUtils.toFloatArray(bank.dominantHeights), is(arrayContaining(0.0f, Float.NaN, Float.NaN, 35.47338f, Float.NaN, Float.NaN)) diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow11UpdateCompatibilityVariables.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow11UpdateCompatibilityVariables.java index d71e7e6ed..976c97bc6 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow11UpdateCompatibilityVariables.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow11UpdateCompatibilityVariables.java @@ -59,7 +59,7 @@ void testStandardPath() throws ProcessingException, ValueParseException { fpe.processPolygon(polygon, ExecutionStep.GROW_11_COMPATIBILITY_VARS); // VDYP7 reports [], -9, -9, 35.473381, -9, -9) - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); assertThat( // VDYP7 reports BASAL_AREA = -2.13947629e-07, all others 0.0 lps.getCvPrimaryLayerSmall()[1], diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow1CalculateDominantHeightDeltaTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow1CalculateDominantHeightDeltaTest.java index 43933a28e..b1a0ec476 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow1CalculateDominantHeightDeltaTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow1CalculateDominantHeightDeltaTest.java @@ -32,7 +32,6 @@ import ca.bc.gov.nrs.vdyp.io.parse.common.ResourceParseException; import ca.bc.gov.nrs.vdyp.io.parse.streaming.StreamingParser; import ca.bc.gov.nrs.vdyp.io.parse.streaming.StreamingParserFactory; -import ca.bc.gov.nrs.vdyp.model.LayerType; import ca.bc.gov.nrs.vdyp.model.PolygonIdentifier; import ca.bc.gov.nrs.vdyp.model.VdypPolygon; @@ -69,7 +68,7 @@ void testNormalCurve() throws ProcessingException { var polygon = forwardDataStreamReader.readNextPolygon().orElseThrow(); // Select the first polygon - 01002 S000001 00(1970) - fpe.fps.setPolygonLayer(polygon, LayerType.PRIMARY); + fpe.fps.setPolygon(polygon); float hd = 35.2999992f; int sc = 13; @@ -92,7 +91,7 @@ void testCurveExtension1() throws ProcessingException { polygon = forwardDataStreamReader.readNextPolygon().orElseThrow(); } while (!polygon.getPolygonIdentifier().getName().equals("01003AS000001 00")); - fpe.fps.setPolygonLayer(polygon, LayerType.PRIMARY); + fpe.fps.setPolygon(polygon); float hd = 29.5f; int sc = 11; @@ -115,7 +114,7 @@ void testCurveExtension2() throws ProcessingException { polygon = forwardDataStreamReader.readNextPolygon().orElseThrow(); } while (!polygon.getPolygonIdentifier().getName().equals("01003AS000001 00")); - fpe.fps.setPolygonLayer(polygon, LayerType.PRIMARY); + fpe.fps.setPolygon(polygon); fpe.processPolygon(polygon, ExecutionStep.GROW_1_LAYER_DHDELTA.predecessor()); diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow4CalculateLoreyHeightEstimatesTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow4CalculateLoreyHeightEstimatesTest.java index 19ced065c..c5b40e4b6 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow4CalculateLoreyHeightEstimatesTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow4CalculateLoreyHeightEstimatesTest.java @@ -57,7 +57,7 @@ void testStandardPath() throws ProcessingException { VdypPolygon polygon = forwardDataStreamReader.readNextPolygon().orElseThrow(); fpe.processPolygon(polygon, ExecutionStep.GROW_4_LAYER_BA_AND_DQTPH_EST); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); float dhStart = 35.3f; float dhEnd = 35.473381f; @@ -85,7 +85,7 @@ void testDebug8Setting2Path() throws ProcessingException { VdypPolygon polygon = forwardDataStreamReader.readNextPolygon().orElseThrow(); fpe.processPolygon(polygon, ExecutionStep.GROW_4_LAYER_BA_AND_DQTPH_EST); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); float dhStart = 35.3f; float dhEnd = 35.3f; diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow5SpeciesBaDqTphTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow5SpeciesBaDqTphTest.java index 4a9aa64cd..02b945297 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow5SpeciesBaDqTphTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow5SpeciesBaDqTphTest.java @@ -57,7 +57,7 @@ void testStandardPath() throws ProcessingException { VdypPolygon polygon = forwardDataStreamReader.readNextPolygon().orElseThrow(); fpe.processPolygon(polygon, ExecutionStep.GROW_5A_LH_EST); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); float baStart = 45.3864441f; float baDelta = 0.351852179f; @@ -110,7 +110,7 @@ void testGrowUsingNoSpeciesDynamics() throws ProcessingException { VdypPolygon polygon = forwardDataStreamReader.readNextPolygon().orElseThrow(); fpe.processPolygon(polygon, ExecutionStep.GROW_4_LAYER_BA_AND_DQTPH_EST); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); float baChangeRate = 0.00775236264f; float tphChangeRate = 0.987927794f; @@ -152,7 +152,7 @@ void testGrowUsingFullSpeciesDynamics() throws ProcessingException { VdypPolygon polygon = forwardDataStreamReader.readNextPolygon().orElseThrow(); fpe.processPolygon(polygon, ExecutionStep.GROW_4_LAYER_BA_AND_DQTPH_EST); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); fpe.fps.fcm.getDebugSettings().setValue(Vars.SPECIES_DYNAMICS_1, 0); diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow6TreesPerHectareTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow6TreesPerHectareTest.java index f4c1883ac..1c6843669 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow6TreesPerHectareTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow6TreesPerHectareTest.java @@ -57,7 +57,7 @@ void testStandardPath() throws ProcessingException { fpe.processPolygon(polygon, ExecutionStep.GROW_6_LAYER_TPH2); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); var calculatedLayerTph = lps.getBank().treesPerHectare[0][UtilizationClass.ALL.ordinal()]; diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow7QuadMeanDiameterTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow7QuadMeanDiameterTest.java index 11e634679..e42870fb0 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow7QuadMeanDiameterTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow7QuadMeanDiameterTest.java @@ -57,7 +57,7 @@ void testStandardPath() throws ProcessingException { fpe.processPolygon(polygon, ExecutionStep.GROW_7_LAYER_DQ2); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); var calculatedLayerDq = lps.getBank().quadMeanDiameters[0][UtilizationClass.ALL.ordinal()]; diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow8PerSpeciesLoreyHeightTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow8PerSpeciesLoreyHeightTest.java index 37b9724b4..2d084e1ee 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow8PerSpeciesLoreyHeightTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow8PerSpeciesLoreyHeightTest.java @@ -59,7 +59,7 @@ void testStandardPath() throws ProcessingException { fpe.fps.fcm.getDebugSettings().setValue(Vars.LOREY_HEIGHT_CHANGE_STRATEGY_8, 0); fpe.processPolygon(polygon, ExecutionStep.GROW_8_SPECIES_LH); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); var calculatedLayerDq = lps.getBank().quadMeanDiameters[0][UtilizationClass.ALL.ordinal()]; @@ -78,7 +78,7 @@ void testDebug8Setting2() throws ProcessingException { fpe.fps.fcm.getDebugSettings().setValue(Vars.LOREY_HEIGHT_CHANGE_STRATEGY_8, 2); fpe.processPolygon(polygon, ExecutionStep.GROW_8_SPECIES_LH); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); var calculatedLayerDq = lps.getBank().quadMeanDiameters[0][UtilizationClass.ALL.ordinal()]; diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow9PercentagesOfForestedLand.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow9PercentagesOfForestedLand.java index d6503d7af..6b988f3aa 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow9PercentagesOfForestedLand.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/Grow9PercentagesOfForestedLand.java @@ -58,7 +58,7 @@ void testStandardPath() throws ProcessingException, ValueParseException { fpe.processPolygon(polygon, ExecutionStep.GROW_9_SPECIES_PCT); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); // VDYP7 value is 0.892216682f, 11.5443392f, 64.3765259f, 13.3774729f, 9.80944252f assertThat( diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/GrowAllStepsTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/GrowAllStepsTest.java index 3e19aaa29..a68188598 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/GrowAllStepsTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/GrowAllStepsTest.java @@ -30,8 +30,7 @@ class GrowAllStepsTest { - protected static final Logger logger = LoggerFactory - .getLogger(GrowAllStepsTest.class); + protected static final Logger logger = LoggerFactory.getLogger(GrowAllStepsTest.class); protected static ForwardControlParser parser; protected static Map controlMap; @@ -75,7 +74,7 @@ void testStandardPath() throws ProcessingException, ValueParseException { var nextComparisonPolygonRef = comparisonDataStreamReader.readNextPolygon(); while (nextComparisonPolygonRef.isPresent()) { - + var polygon = forwardDataStreamReader.readNextPolygon().orElseThrow(() -> new WorkCompletedException()); var comparisonPolygon = nextComparisonPolygonRef.get(); @@ -87,24 +86,26 @@ void testStandardPath() throws ProcessingException, ValueParseException { nextComparisonPolygonRef = comparisonDataStreamReader.readNextPolygon(); } - assertThat(polygon.getPolygonIdentifier().forYear(polygon.getTargetYear().get()) - , is(comparisonPolygon.getPolygonIdentifier())); - + assertThat( + polygon.getPolygonIdentifier().forYear(polygon.getTargetYear().get()), + is(comparisonPolygon.getPolygonIdentifier()) + ); + fpe.processPolygon(polygon); - + // comparePolygons(polygon, comparisonPolygon, 0.02f); } } catch (WorkCompletedException e) { assertThat(comparisonDataStreamReader.readNextPolygon().isEmpty(), is(true)); } - + assertThat(forwardDataStreamReader.readNextPolygon().isEmpty(), is(true)); } private static void comparePolygons(VdypPolygon a, VdypPolygon b, float tolerance) { - + VdypMatchers.setEpsilon(tolerance); - + assertThat(a.getPolygonIdentifier().forYear(a.getTargetYear().get()), is(b.getPolygonIdentifier())); assertThat(a.getBiogeoclimaticZone(), is(b.getBiogeoclimaticZone())); assertThat(a.getForestInventoryZone(), is(b.getForestInventoryZone())); @@ -112,24 +113,26 @@ private static void comparePolygons(VdypPolygon a, VdypPolygon b, float toleranc // assertThat(a.getMode(), is(b.getMode())); -- comparison polys don't have modes assertThat(a.getPercentAvailable(), is(b.getPercentAvailable())); assertThat(a.getTargetYear().get(), is(b.getPolygonIdentifier().getYear())); - + assertThat(a.getLayers().size(), is(b.getLayers().size())); - + compareLayers(a.getLayers().get(LayerType.PRIMARY), b.getLayers().get(LayerType.PRIMARY)); // compareLayers(a.getLayers().get(LayerType.VETERAN), b.getLayers().get(LayerType.VETERAN)); } private static void compareLayers(VdypLayer aLayer, VdypLayer bLayer) { if (aLayer != null && bLayer != null) { - + assertThat(aLayer.getLayerType(), is(bLayer.getLayerType())); assertThat(aLayer.getPrimaryGenus(), is(bLayer.getPrimaryGenus())); assertThat(aLayer.getInventoryTypeGroup(), is(bLayer.getInventoryTypeGroup())); assertThat(aLayer.getPolygonIdentifier().getName(), is(bLayer.getPolygonIdentifier().getName())); assertThat(aLayer.getAgeTotal(), is(bLayer.getAgeTotal())); - assertThat(aLayer.getBaseAreaByUtilization(), VdypMatchers.coe(-1, VdypMatchers::closeTo, - bLayer.getBaseAreaByUtilization().toArray(Float[]::new))); - + assertThat( + aLayer.getBaseAreaByUtilization(), + VdypMatchers.coe(-1, VdypMatchers::closeTo, bLayer.getBaseAreaByUtilization().toArray(Float[]::new)) + ); + } else if (aLayer != bLayer) { fail(); } diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/PreliminaryForwardProcessingEngineStepsTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/PreliminaryForwardProcessingEngineStepsTest.java index 339327c60..5f826ff54 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/PreliminaryForwardProcessingEngineStepsTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/PreliminaryForwardProcessingEngineStepsTest.java @@ -22,7 +22,6 @@ import ca.bc.gov.nrs.vdyp.common_calculators.enumerations.SiteIndexEquation; import ca.bc.gov.nrs.vdyp.io.parse.common.ResourceParseException; import ca.bc.gov.nrs.vdyp.model.CommonData; -import ca.bc.gov.nrs.vdyp.model.LayerType; import ca.bc.gov.nrs.vdyp.model.MatrixMap2Impl; import ca.bc.gov.nrs.vdyp.model.Region; import ca.bc.gov.nrs.vdyp.model.VdypEntity; @@ -68,9 +67,9 @@ void testFindPrimarySpecies() throws IOException, ResourceParseException, Proces { ForwardProcessingEngine fpe = new ForwardProcessingEngine(controlMap); - fpe.fps.setPolygonLayer(polygon, LayerType.PRIMARY); + fpe.fps.setPolygon(polygon); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); ForwardProcessingEngine.calculateCoverages(lps); fpe.determinePolygonRankings(CommonData.PRIMARY_SPECIES_TO_COMBINE); @@ -83,8 +82,8 @@ void testFindPrimarySpecies() throws IOException, ResourceParseException, Proces } { ForwardProcessingEngine fpe = new ForwardProcessingEngine(controlMap); - fpe.fps.setPolygonLayer(polygon, LayerType.PRIMARY); - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + fpe.fps.setPolygon(polygon); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); var speciesToCombine = Arrays .asList(Arrays.asList(lps.getBank().speciesNames[3], lps.getBank().speciesNames[4])); @@ -132,11 +131,13 @@ void testGroupAndStratumNumberSpecialCases() throws IOException, ResourceParseEx ForwardProcessingEngine fpe = new ForwardProcessingEngine(controlMap); fpe.processPolygon(polygon, ForwardProcessingEngine.ExecutionStep.DETERMINE_POLYGON_RANKINGS); - assertThat(fpe.fps.getLayerProcessingState().getPrimarySpeciesIndex(), is(1)); - assertThrows(IllegalStateException.class, () -> fpe.fps.getLayerProcessingState().getSecondarySpeciesIndex()); - assertThat(fpe.fps.getLayerProcessingState().getInventoryTypeGroup(), is(9)); - assertThat(fpe.fps.getLayerProcessingState().getPrimarySpeciesGroupNumber(), is(34)); - assertThat(fpe.fps.getLayerProcessingState().getPrimarySpeciesStratumNumber(), is(24)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getPrimarySpeciesIndex(), is(1)); + assertThrows( + IllegalStateException.class, () -> fpe.fps.getPrimaryLayerProcessingState().getSecondarySpeciesIndex() + ); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getInventoryTypeGroup(), is(9)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getPrimarySpeciesGroupNumber(), is(34)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getPrimarySpeciesStratumNumber(), is(24)); } @Test @@ -161,11 +162,11 @@ void testCalculateMissingSiteCurves() throws IOException, ResourceParseException fpe.processPolygon(polygon, ForwardProcessingEngine.ExecutionStep.CALCULATE_MISSING_SITE_CURVES); // Cannot check 0 since determinePolygonRankings has not been executed. - assertThat(fpe.fps.getLayerProcessingState().getSiteCurveNumber(1), is(12)); - assertThat(fpe.fps.getLayerProcessingState().getSiteCurveNumber(2), is(2)); - assertThat(fpe.fps.getLayerProcessingState().getSiteCurveNumber(3), is(42)); - assertThat(fpe.fps.getLayerProcessingState().getSiteCurveNumber(4), is(10)); - assertThat(fpe.fps.getLayerProcessingState().getSiteCurveNumber(5), is(10)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getSiteCurveNumber(1), is(118)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getSiteCurveNumber(2), is(122)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getSiteCurveNumber(3), is(13)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getSiteCurveNumber(4), is(99)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getSiteCurveNumber(5), is(59)); } @Test @@ -197,11 +198,11 @@ void testCalculateMissingSiteCurvesNoSiteCurveData() fpe.processPolygon(polygon, ForwardProcessingEngine.ExecutionStep.CALCULATE_MISSING_SITE_CURVES); // Cannot check 0 since determinePolygonRankings has not been executed. - assertThat(fpe.fps.getLayerProcessingState().getSiteCurveNumber(1), is(118)); - assertThat(fpe.fps.getLayerProcessingState().getSiteCurveNumber(2), is(122)); - assertThat(fpe.fps.getLayerProcessingState().getSiteCurveNumber(3), is(13)); - assertThat(fpe.fps.getLayerProcessingState().getSiteCurveNumber(4), is(99)); - assertThat(fpe.fps.getLayerProcessingState().getSiteCurveNumber(5), is(59)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getSiteCurveNumber(1), is(118)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getSiteCurveNumber(2), is(122)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getSiteCurveNumber(3), is(13)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getSiteCurveNumber(4), is(99)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getSiteCurveNumber(5), is(59)); } @Test @@ -246,7 +247,9 @@ void testEstimateMissingSiteIndicesStep1() throws ProcessingException, IOExcepti // double expectedValue = SiteTool // .convertSiteIndexBetweenCurves(sourceSiteCurve, sourceSiteIndex, targetSiteCurve); - assertThat(fpe.fps.getLayerProcessingState().getBank().siteIndices[4], is(VdypEntity.MISSING_FLOAT_VALUE)); + assertThat( + fpe.fps.getPrimaryLayerProcessingState().getBank().siteIndices[4], is(VdypEntity.MISSING_FLOAT_VALUE) + ); } @Test @@ -287,7 +290,7 @@ void testEstimateMissingSiteIndicesStep2() throws ProcessingException, IOExcepti double expectedValue = SiteTool .convertSiteIndexBetweenCurves(sourceSiteCurve, sourceSiteIndex, targetSiteCurve); - assertThat(fpe.fps.getLayerProcessingState().getBank().siteIndices[2], is((float) expectedValue)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getBank().siteIndices[2], is((float) expectedValue)); } @Test @@ -315,7 +318,7 @@ void testEstimateMissingYearsToBreastHeightValues() ); assertThat( - fpe.fps.getLayerProcessingState().getBank().yearsToBreastHeight, + fpe.fps.getPrimaryLayerProcessingState().getBank().yearsToBreastHeight, is(new float[] { 0.0f, 4.7f, 4.6f, 1.0f, 5.0f, 5.0f }) ); } @@ -387,10 +390,10 @@ void testCalculateDominantHeightAgeSiteIndexNoSecondary() ForwardProcessingEngine fpe = new ForwardProcessingEngine(controlMap); fpe.processPolygon(polygon, ForwardProcessingEngine.ExecutionStep.CALCULATE_DOMINANT_HEIGHT_AGE_SITE_INDEX); - assertThat(fpe.fps.getLayerProcessingState().getPrimarySpeciesDominantHeight(), is(22.950302f)); - assertThat(fpe.fps.getLayerProcessingState().getPrimarySpeciesSiteIndex(), is(34.0f)); - assertThat(fpe.fps.getLayerProcessingState().getPrimarySpeciesTotalAge(), is(22.0f)); - assertThat(fpe.fps.getLayerProcessingState().getPrimarySpeciesAgeAtBreastHeight(), is(Float.NaN)); - assertThat(fpe.fps.getLayerProcessingState().getPrimarySpeciesAgeToBreastHeight(), is(4.7f)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getPrimarySpeciesDominantHeight(), is(22.950302f)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getPrimarySpeciesSiteIndex(), is(34.0f)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getPrimarySpeciesTotalAge(), is(22.0f)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getPrimarySpeciesAgeAtBreastHeight(), is(Float.NaN)); + assertThat(fpe.fps.getPrimaryLayerProcessingState().getPrimarySpeciesAgeToBreastHeight(), is(4.7f)); } } diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/PreliminarySetCompatibilityVariablesTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/PreliminarySetCompatibilityVariablesTest.java index 6699410ca..4f64170b4 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/PreliminarySetCompatibilityVariablesTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/PreliminarySetCompatibilityVariablesTest.java @@ -45,7 +45,7 @@ void testSetCompatibilityVariables() throws ResourceParseException, IOException, // These values have been verified against the FORTRAN implementation, allowing for minor // platform-specific differences. - LayerProcessingState lps = fpe.fps.getLayerProcessingState(); + LayerProcessingState lps = fpe.fps.getPrimaryLayerProcessingState(); assertThat( lps.getVolumeEquationGroups(), diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/SetEquationGroupsTest.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/SetEquationGroupsTest.java index 311217778..741b380d6 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/SetEquationGroupsTest.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/SetEquationGroupsTest.java @@ -9,7 +9,6 @@ import ca.bc.gov.nrs.vdyp.application.ProcessingException; import ca.bc.gov.nrs.vdyp.io.parse.common.ResourceParseException; -import ca.bc.gov.nrs.vdyp.model.LayerType; import ca.bc.gov.nrs.vdyp.model.VdypEntity; public class SetEquationGroupsTest extends AbstractForwardProcessingEngineTest { @@ -21,18 +20,18 @@ void testSetEquationGroups() throws ResourceParseException, IOException, Process var polygon = reader.readNextPolygon().get(); ForwardProcessingState fps = new ForwardProcessingState(controlMap); - fps.setPolygonLayer(polygon, LayerType.PRIMARY); + fps.setPolygon(polygon); assertThat( - fps.getLayerProcessingState().getVolumeEquationGroups(), + fps.getPrimaryLayerProcessingState().getVolumeEquationGroups(), Matchers.is(new int[] { VdypEntity.MISSING_INTEGER_VALUE, 12, 20, 25, 37, 66 }) ); assertThat( - fps.getLayerProcessingState().getDecayEquationGroups(), + fps.getPrimaryLayerProcessingState().getDecayEquationGroups(), Matchers.is(new int[] { VdypEntity.MISSING_INTEGER_VALUE, 7, 14, 19, 31, 54 }) ); assertThat( - fps.getLayerProcessingState().getBreakageEquationGroups(), + fps.getPrimaryLayerProcessingState().getBreakageEquationGroups(), Matchers.is(new int[] { VdypEntity.MISSING_INTEGER_VALUE, 5, 6, 12, 17, 28 }) ); } diff --git a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/test/Vdyp7OutputControlParser.java b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/test/Vdyp7OutputControlParser.java index 5906f47c1..b3d57f6c4 100644 --- a/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/test/Vdyp7OutputControlParser.java +++ b/lib/vdyp-forward/src/test/java/ca/bc/gov/nrs/vdyp/forward/test/Vdyp7OutputControlParser.java @@ -62,9 +62,9 @@ protected List outputFileParsers() { @Override protected ValueParser> minimaParser() { return ValueParser.toMap( - ValueParser.list(ValueParser.FLOAT), Collections.singletonMap(MINIMUM_VETERAN_HEIGHT, 10.0f), - MINIMUM_HEIGHT, MINIMUM_BASE_AREA, MINIMUM_PREDICTED_BASE_AREA, MINIMUM_VETERAN_HEIGHT - ); + ValueParser.list(ValueParser.FLOAT), Collections.singletonMap(MINIMUM_VETERAN_HEIGHT, 10.0f), + MINIMUM_HEIGHT, MINIMUM_BASE_AREA, MINIMUM_PREDICTED_BASE_AREA, MINIMUM_VETERAN_HEIGHT + ); } private final List orderedControlKeys = new ArrayList<>(); diff --git a/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP-Checkpoint.CTR b/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP-Checkpoint.CTR index 0a9bbf837..60bcaf7aa 100755 --- a/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP-Checkpoint.CTR +++ b/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP-Checkpoint.CTR @@ -24,6 +24,7 @@ 022 coe/BGRP.DAT Defines Breakage Groups RD_BGRP IPSJF157 025 coe/SIEQN.PRM Site Curve Numbers assigned +025 Nullifies above siteCurve # 026 coe/SIAGEMAX.PRM MAXIMUM AGES FOR HT INCR, BY SITE CURVE NUMBER (SIAGEMAX.prm=140) 028 coe/CVADJ.PRM CV adjustment and relalted parameters diff --git a/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP-NoSiteCurves.CTR b/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP-SiteCurves.CTR similarity index 97% rename from lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP-NoSiteCurves.CTR rename to lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP-SiteCurves.CTR index 853397bc4..4910417a0 100755 --- a/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP-NoSiteCurves.CTR +++ b/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP-SiteCurves.CTR @@ -24,7 +24,6 @@ 022 coe/BGRP.DAT Defines Breakage Groups RD_BGRP IPSJF157 025 coe/SIEQN.PRM Site Curve Numbers assigned -025 Nullifies above siteCurve # 026 coe/SIAGEMAX.PRM MAXIMUM AGES FOR HT INCR, BY SITE CURVE NUMBER (SIAGEMAX.prm=140) 028 coe/CVADJ.PRM CV adjustment and relalted parameters diff --git a/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP.CTR b/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP.CTR index 4910417a0..853397bc4 100755 --- a/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP.CTR +++ b/lib/vdyp-forward/src/test/resources/ca/bc/gov/nrs/vdyp/test/VDYP.CTR @@ -24,6 +24,7 @@ 022 coe/BGRP.DAT Defines Breakage Groups RD_BGRP IPSJF157 025 coe/SIEQN.PRM Site Curve Numbers assigned +025 Nullifies above siteCurve # 026 coe/SIAGEMAX.PRM MAXIMUM AGES FOR HT INCR, BY SITE CURVE NUMBER (SIAGEMAX.prm=140) 028 coe/CVADJ.PRM CV adjustment and relalted parameters diff --git a/lib/vdyp-sindex/src/main/java/ca/bc/gov/nrs/vdyp/sindex/Sindxdll.java b/lib/vdyp-sindex/src/main/java/ca/bc/gov/nrs/vdyp/sindex/Sindxdll.java index 6f31c3b34..fd803c6ed 100644 --- a/lib/vdyp-sindex/src/main/java/ca/bc/gov/nrs/vdyp/sindex/Sindxdll.java +++ b/lib/vdyp-sindex/src/main/java/ca/bc/gov/nrs/vdyp/sindex/Sindxdll.java @@ -2921,7 +2921,7 @@ public static int Y2BH(SiteIndexEquation curve, double siteIndex, Reference resultSiteIndex = new Reference<>(); - Sindxdll.SIToSI(SI_SPEC_AT, 10.0, SI_SPEC_AT, resultSiteIndex); - assertEquals(10.0f, resultSiteIndex.get()); + assertThrows(NoAnswerException.class, () -> { + Sindxdll.SIToSI(SI_SPEC_AT, 10.0, SI_SPEC_AT, resultSiteIndex); + }); } }