Horizon.java [src/soils] Revision: default Date:
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package soils;
import csip.api.server.ServiceException;
import csip.utils.JSONUtils;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.codehaus.jettison.json.JSONArray;
import org.codehaus.jettison.json.JSONException;
import org.codehaus.jettison.json.JSONObject;
import static soils.Fragments.FRAGMENTS_LIST;
import static soils.TextureGroup.TEXTURE_GROUP_LIST;
import soils.db.tables.TableHorizon;
import soils.db.tables.TableHorizonCalculations;
import soils.exceptions.SDMException;
import soils.exceptions.WEPPException;
import soils.utils.EvalResult;
import soils.utils.SoilUtils;
/**
*
* @author <a href="mailto:shaun.case@colostate.edu">Shaun Case</a>
*/
public class Horizon {
protected static ArrayList<String> horizonRequiredInputs = new ArrayList<>();
protected static ArrayList<String> horizonUsedColumns = new ArrayList<>();
protected static ArrayList<String> organicTextures = new ArrayList<>(Arrays.asList(
"hpm",
"mpm",
"spm",
//"mat", //?? This is an ignorable "cemented" layer isn't it??
"mk-cl",
"muck",
"mpt",
"peat",
"pdom",
"udom",
"ce",
"de"
));
protected static ArrayList<String> restrictingTextures = new ArrayList<>(Arrays.asList(
"cem-mat",
"cem",
"cem-s",
"br",
"dur",
"ind",
"or",
"opwd",
"pc",
"pf",
"pgp",
"uwb",
"wb"
));
protected static ArrayList<String> restrictingTexturesPartialMatches = new ArrayList<>(Arrays.asList(
"cem-",
"cem ",
" cem ",
" cem",
"pf-" //Perma-frost
));
//These will get removed from their component before WEPP or WEPS runs...
protected static ArrayList<String> nonCementedRestrictingLayers = new ArrayList<>(Arrays.asList(
"cind",
"frag",
"gyp",
"marl",
"pum",
"u",
"var",
"w",
"mat",
"sg",
"art",
"by",
"cb",
"cn",
"fl",
"g",
"st"
));
protected static ArrayList<String> ignoredTextureIfNotSurface = new ArrayList<>(Arrays.asList(
"fine gypsum material"
));
protected static final String[] TEXTURE_CHK = {"by", "cem", "ce", "dur", "frag", "gyp", "hpm", "ind", "marl", "mat",
"mpm", "muck", "mpt", "or", "opwd",
"peat", "pc", "pf", "pgp", "pum", "spm", "st", "udom",
"u", "uwb", "var", "w", "wb", "cem-", "pf-"};
public synchronized static void setRequiredInputs(List<String> horizonInputs) {
horizonRequiredInputs.clear();
if (null != horizonInputs) {
horizonRequiredInputs.addAll(horizonInputs);
horizonUsedColumns.addAll(horizonInputs);
}
}
public synchronized static void setDefaultUsedColumns(List<String> usedColumns) {
horizonUsedColumns.clear();
if (null != usedColumns) {
horizonUsedColumns.addAll(usedColumns);
}
}
public synchronized static ArrayList<String> getDefaultUsedColumns() {
return ((null != horizonUsedColumns) ? ((ArrayList<String>) horizonUsedColumns.clone()) : null);
}
public synchronized static ArrayList<String> getRequiedInputs() {
return ((null != horizonRequiredInputs) ? ((ArrayList<String>) horizonRequiredInputs.clone()) : null);
}
private boolean selected = false;
private ArrayList<String> selectedReason = new ArrayList<>();
protected TableHorizon tableHorizon = new TableHorizon();
protected TableHorizonCalculations tableHorizonCalculations = new TableHorizonCalculations();
public LinkedHashMap<String, TextureGroup> textureGroups;
public LinkedHashMap<String, Fragments> fragments;
private double conductivity = Double.NaN;
private double interrill = Double.NaN;
private double rill = Double.NaN;
private double shear = Double.NaN;
private boolean surface = false;
private boolean restricting = false;
private boolean permiable = false;
private Boolean mineral = null;
private boolean useGenericHz1Values = false;
private boolean useGenericHz2Values = false;
private double fieldCapacitySWC;
private double wiltingPointSWC;
private double soilPh;
/*
public String chkey;
public double om_r;
public double hzthk_r;
public double hzdept_r;
public double hzdepb_r;
public double kwfact;
public double kffact;
public double lsfact;
public double sandtotal_r; //AKA sand_pct
*/
public Horizon() {
fragments = new LinkedHashMap<>();
textureGroups = new LinkedHashMap<>();
tableHorizon.setUsedColumns(horizonUsedColumns);
tableHorizon.setRequiredColumns(horizonRequiredInputs);
tableHorizonCalculations.setRequiredColumns(horizonRequiredInputs);
tableHorizonCalculations.setUsedColumns(horizonUsedColumns);
selectedReason.add("ANY");
}
public Horizon(JSONArray dataJSON) throws ServiceException, JSONException {
Map<String, JSONObject> horizonsDataArray = JSONUtils.preprocess(dataJSON);
if ((null != dataJSON) && (dataJSON.length() > 0)) {
tableHorizon.setUsedColumns(horizonUsedColumns);
tableHorizon.setRequiredColumns(horizonRequiredInputs);
tableHorizonCalculations.setRequiredColumns(horizonRequiredInputs);
tableHorizonCalculations.setUsedColumns(horizonUsedColumns);
tableHorizon.readValuesFromJSON(dataJSON);
tableHorizonCalculations.readValuesFromJSON(dataJSON);
selectedReason.add("ANY");
selected = true;
fragments = new LinkedHashMap<>();//We dont' currently use this, yet.
textureGroups = new LinkedHashMap<>();
setTextureGroups(JSONUtils.getJSONArrayParam(horizonsDataArray, TEXTURE_GROUP_LIST));
} else {
throw new ServiceException("No mapunit JSON specified. A NULL or empty value was passed to SOILS_DATA.MapUnit()");
}
}
public Horizon(ResultSet results) throws ServiceException {
tableHorizon.setRequiredColumns(horizonRequiredInputs);
tableHorizon.setUsedColumns(horizonUsedColumns);
tableHorizonCalculations.setRequiredColumns(horizonRequiredInputs);
tableHorizonCalculations.setUsedColumns(horizonUsedColumns);
selectedReason.add("ANY");
tableHorizon.readValuesFromSQL(results);
tableHorizonCalculations.readValuesFromSQL(results);
fragments = new LinkedHashMap<>();//We dont' currently use this, yet.
textureGroups = new LinkedHashMap<>();
}
private void setTextureGroups(JSONArray dataJSON) throws ServiceException, JSONException {
if ((null != dataJSON) && (dataJSON.length() > 0)) {
for (int i = 0; i < dataJSON.length(); i++) {
TextureGroup textureGroup = new TextureGroup(dataJSON.getJSONArray(i));
if (!textureGroups.containsKey(textureGroup.chtgkey())) {
textureGroups.put(textureGroup.chtgkey(), textureGroup);
} else {
throw new ServiceException("Duplicate component passed to Component.setTextureGroups() from input JSON. Texture group keys listed by horizon should be unique.");
}
}
}
}
@Deprecated
public void setTextureGroups(ResultSet results) throws SQLException, ServiceException {
if (null != results) {
TextureGroup textureGroup = new TextureGroup();
textureGroup.readFromSQL(results);
textureGroups.put(textureGroup.chtgkey(), textureGroup);
}
}
public void setTextureGroups(ResultSet results, ArrayList<String> columnsUsed, ArrayList<String> textureColumns) throws SQLException, ServiceException {
if (null != results) {
if ((null != columnsUsed) && (!columnsUsed.isEmpty())) {
TextureGroup textureGroup = new TextureGroup();
textureGroup.setUsedColumns(columnsUsed);
textureGroup.readFromSQL(results, textureColumns);
textureGroups.put(textureGroup.chtgkey(), textureGroup);
}
} else {
throw new ServiceException("NULL ResultSet passed to setTextureGropus. Cannot continue.");
}
}
// public boolean readAllTextureData(ResultSet results) throws SQLException, ServiceException {
// boolean ret_val = false;
// if (null != results) {
// while (results.next()) {
//
// }
// }
//
// return ret_val;
// }
@Deprecated
public void setFragments(ResultSet results) throws SQLException, ServiceException {
while (results.next()) {
boolean matchFound = false;
Fragments tFragment = new Fragments();
tFragment.readFromSQL(results);
for (Fragments fragment : fragments.values()) {
if (fragment.isEqual(tFragment)) {
matchFound = true;
break;
}
}
if (!matchFound) {
fragments.put(tFragment.chfragskey(), tFragment);
}
}
}
public void setFragments(ResultSet results, List<String> usedColumns) throws SQLException, ServiceException {
if (null != results) {
if (null != usedColumns) {
while (results.next()) {
boolean matchFound = false;
Fragments tFragment = new Fragments();
tFragment.setUsedColumns(usedColumns);
tFragment.readFromSQL(results);
for (Fragments fragment : fragments.values()) {
if (fragment.isEqual(tFragment)) {
matchFound = true;
break;
}
}
if (!matchFound) {
fragments.put(tFragment.chfragskey(), tFragment);
}
}
} else {
throw new ServiceException("No used column list was passed to setFragments function.");
}
} else {
throw new ServiceException("NULL ResultSet was passed to setFragments funciton.");
}
}
public LinkedHashMap<String, TextureGroup> textureGroups() {
return this.textureGroups;
}
public void readFromSQL(ResultSet results) throws ServiceException {
tableHorizon.readValuesFromSQL(results);
tableHorizonCalculations.readValuesFromSQL(results);
//Update depth inches conversions in calculations table.
hzdepb_r_in();
hzdept_r_in();
}
public final void fieldCapacitySWC(double value) {
fieldCapacitySWC = value;
}
public final void wiltingPointSWC(double value) {
wiltingPointSWC = value;
}
public final void soilPh(double value) {
soilPh = value;
}
public final double fieldCapacitySWC() {
return fieldCapacitySWC;
}
public final double wiltingPointSWC() {
return wiltingPointSWC;
}
public final double soilPh() {
return soilPh;
}
public final void sar_r(double value) {
tableHorizon.sar_r(value);
}
public final double sar_r() {
return tableHorizon.sar_r();
}
public final void ec_r(double value) {
tableHorizon.ec_r(value);
}
public final double ec_r() {
return tableHorizon.ec_r();
}
public final void hzdept_l(double value) {
tableHorizon.hzdept_l(value);
}
public final double hzdept_l() {
return tableHorizon.hzdept_l();
}
public final void hzdept_h(double value) {
tableHorizon.hzdept_h(value);
}
public final double hzdept_h() {
return tableHorizon.hzdept_h();
}
public final void hzdepb_l(double value) {
tableHorizon.hzdepb_l(value);
}
public final double hzdepb_l() {
return tableHorizon.hzdepb_l();
}
public final void hzdepb_h(double value) {
tableHorizon.hzdepb_h(value);
}
public final double hzdepb_h() {
return tableHorizon.hzdepb_h();
}
public final void sandvc_l(double value) {
tableHorizon.sandvc_l(value);
}
public final double sandvc_l() {
return tableHorizon.sandvc_l();
}
public final void sandvc_r(double value) {
tableHorizon.sandvc_r(value);
}
public final double sandvc_r() {
return tableHorizon.sandvc_r();
}
public final void sandvc_h(double value) {
tableHorizon.sandvc_h(value);
}
public final double sandvc_h() {
return tableHorizon.sandvc_h();
}
public final void sandco_l(double value) {
tableHorizon.sandco_l(value);
}
public final double sandco_l() {
return tableHorizon.sandco_l();
}
public final void sandco_r(double value) {
tableHorizon.sandco_r(value);
}
public final double sandco_r() {
return tableHorizon.sandco_r();
}
public final void sandco_h(double value) {
tableHorizon.sandco_h(value);
}
public final double sandco_h() {
return tableHorizon.sandco_h();
}
public final void sandmed_l(double value) {
tableHorizon.sandmed_l(value);
}
public final double sandmed_l() {
return tableHorizon.sandmed_l();
}
public final void sandmed_r(double value) {
tableHorizon.sandmed_r(value);
}
public final double sandmed_r() {
return tableHorizon.sandmed_r();
}
public final void sandmed_h(double value) {
tableHorizon.sandmed_h(value);
}
public final double sandmed_h() {
return tableHorizon.sandmed_h();
}
public final void sandfine_l(double value) {
tableHorizon.sandfine_l(value);
}
public final double sandfine_l() {
return tableHorizon.sandfine_l();
}
public final void sandfine_r(double value) {
tableHorizon.sandfine_r(value);
}
public final double sandfine_r() {
return tableHorizon.sandfine_r();
}
public final void sandfine_h(double value) {
tableHorizon.sandfine_h(value);
}
public final double sandfine_h() {
return tableHorizon.sandfine_h();
}
public final void sandvf_l(double value) {
tableHorizon.sandvf_l(value);
}
public final double sandvf_l() {
return tableHorizon.sandvf_l();
}
public final void sandvf_r(double value) {
tableHorizon.sandvf_r(value);
}
public final double sandvf_r() {
return tableHorizon.sandvf_r();
}
public final void sandvf_h(double value) {
tableHorizon.sandvf_h(value);
}
public final double sandvf_h() {
return tableHorizon.sandvf_h();
}
public void useGenericSolParams(boolean value) {
useGenericHz1Values = value;
}
public boolean useGenericHz1Values() {
return useGenericHz1Values;
}
public boolean useGenericHz2Values() {
return useGenericHz2Values;
}
public final void wtenthbar_l(double value) {
tableHorizon.wtenthbar_l(value);
}
public final double wtenthbar_l() {
return tableHorizon.wtenthbar_l();
}
public final void wtenthbar_r(double value) {
tableHorizon.wtenthbar_r(value);
}
public final double wtenthbar_r() {
return tableHorizon.wtenthbar_r();
}
public final void wtenthbar_h(double value) {
tableHorizon.wtenthbar_h(value);
}
public final double wtenthbar_h() {
return tableHorizon.wtenthbar_h();
}
public final void ecec_l(double value) {
tableHorizon.ecec_l(value);
}
public final double ecec_l() {
return tableHorizon.ecec_l();
}
public final void ecec_r(double value) {
tableHorizon.ecec_r(value);
}
public final double ecec_r() {
return tableHorizon.ecec_r();
}
public final void ecec_h(double value) {
tableHorizon.ecec_h(value);
}
public final double ecec_h() {
return tableHorizon.ecec_h();
}
public final void caco3_l(double value) {
tableHorizon.caco3_l(value);
}
public final double caco3_l() {
return tableHorizon.caco3_l();
}
public final void caco3_r(double value) {
tableHorizon.caco3_r(value);
}
public final double caco3_r() {
return tableHorizon.caco3_r();
}
public final void caco3_h(double value) {
tableHorizon.caco3_h(value);
}
public final double caco3_h() {
return tableHorizon.caco3_h();
}
public final void ph01mcacl2_l(double value) {
tableHorizon.ph01mcacl2_l(value);
}
public final double ph01mcacl2_l() {
return tableHorizon.ph01mcacl2_l();
}
public final void ph01mcacl2_r(double value) {
tableHorizon.ph01mcacl2_r(value);
}
public final double ph01mcacl2_r() {
return tableHorizon.ph01mcacl2_r();
}
public final void ph01mcacl2_h(double value) {
tableHorizon.ph01mcacl2_h(value);
}
public final double ph01mcacl2_h() {
return tableHorizon.ph01mcacl2_h();
}
public final void lep_l(double value) {
tableHorizon.lep_l(value);
}
public final double lep_l() {
return tableHorizon.lep_l();
}
public final void lep_r(double value) {
tableHorizon.lep_r(value);
}
public final double lep_r() {
return tableHorizon.lep_r();
}
public final void lep_h(double value) {
tableHorizon.lep_h(value);
}
public final double lep_h() {
return tableHorizon.lep_h();
}
public final void ksat_l(double value) {
tableHorizon.ksat_l(value);
}
public final double ksat_l() {
return tableHorizon.ksat_l();
}
public final void ksat_r(double value) {
tableHorizon.ksat_r(value);
}
public final double ksat_r() {
return tableHorizon.ksat_r();
}
public final void ksat_h(double value) {
tableHorizon.ksat_h(value);
}
public final double ksat_h() {
return tableHorizon.ksat_h();
}
public final void hzname(String value) {
tableHorizon.hzname(value);
}
public final String hzname() {
return tableHorizon.hzname();
}
public final void desgnmaster(String value) {
tableHorizon.desgnmaster(value);
}
public final String desgnmaster() {
return tableHorizon.desgnmaster();
}
public Horizon deepCopy() {
Horizon newHorizon = new Horizon();
deepCopy(newHorizon);
return newHorizon;
}
public void deepCopy(Horizon newHorizon) {
if (null != newHorizon) {
tableHorizon.deepCopy(newHorizon.tableHorizon);
tableHorizonCalculations.deepCopy(newHorizon.tableHorizonCalculations);
LinkedHashMap<String, Fragments> tFragments = new LinkedHashMap<>();
for (Fragments tValue : fragments.values()) {
Fragments newValue = tValue.deepCopy();
if (null != newValue) {
tFragments.put(newValue.chfragskey(), newValue);
}
}
if (tFragments.size() > 0) {
newHorizon.setFragments(tFragments);
}
LinkedHashMap<String, TextureGroup> tTGroups = new LinkedHashMap<>();
for (TextureGroup tValue : textureGroups.values()) {
TextureGroup newValue = tValue.deepCopy();
if (null != newValue) {
tTGroups.put(newValue.chtgkey(), newValue);
}
}
if (tTGroups.size() > 0) {
newHorizon.setTextureGroups(tTGroups);
}
newHorizon.conductivity(conductivity);
newHorizon.interrill(interrill);
newHorizon.rill(rill);
newHorizon.shear(shear);
newHorizon.surface(surface);
newHorizon.restricting(restricting);
newHorizon.permiable(permiable);
if (null != mineral) {
newHorizon.mineral(mineral);
} else {
try {
newHorizon.evaluateMineral();
} catch (SDMException ex) {
Logger.getLogger(Horizon.class.getName()).log(Level.SEVERE, null, ex);
}
}
newHorizon.useGenericHz1Values(useGenericHz1Values);
newHorizon.useGenericHz2Values(useGenericHz2Values);
newHorizon.selected(selected());
for (String reason : selectedReason) {
newHorizon.selectedReason(reason);
}
}
}
public void setFragments(Map<String, Fragments> tFragments) {
if ((null != tFragments) && (tFragments.size() > 0)) {
fragments.clear();
for (Fragments tFragment : tFragments.values()) {
if (!fragments.containsKey(tFragment.chfragskey())) {
fragments.put(tFragment.chfragskey(), tFragment);
}
}
}
}
public void setTextureGroups(Map<String, TextureGroup> tTGroups) {
if ((null != tTGroups) && (tTGroups.size() > 0)) {
textureGroups.clear();
for (TextureGroup tTGroup : tTGroups.values()) {
if (!textureGroups.containsKey(tTGroup.chtgkey())) {
textureGroups.put(tTGroup.chtgkey(), tTGroup);
}
}
}
}
public void conductivity(double value) {
conductivity = value;
}
public void interrill(double value) {
interrill = value;
}
public void rill(double value) {
rill = value;
}
public void shear(double value) {
shear = value;
}
public void surface(boolean value) {
surface = value;
}
public void restricting(boolean value) {
restricting = value;
}
public void permiable(boolean value) {
permiable = value;
}
public void mineral(boolean value) {
mineral = value;
}
public String hasWeppWepsParams(String testModel) {
String errorMessage = "";
switch (testModel.toLowerCase()) {
case "wepp":
errorMessage += testWEPP();
break;
case "weps":
errorMessage += testWEPS();
break;
default:
errorMessage += testWEPP();
errorMessage += testWEPS();
}
return errorMessage;
}
protected String testWEPS() {
String errorMessage = "";
//First average all potentially missing values if possible.
hzdept_r(SoilUtils.averageMissingValue(hzdept_h(), hzdept_l(), hzdept_r()));
hzdepb_r(SoilUtils.averageMissingValue(hzdepb_h(), hzdepb_l(), hzdepb_r()));
claytotal_r(SoilUtils.averageMissingValue(claytotal_h(), claytotal_l(), claytotal_r()));
sandtotal_r(SoilUtils.averageMissingValue(sandtotal_h(), sandtotal_l(), sandtotal_r())); // may be useless because the query removes null sandtotals
silttotal_r(SoilUtils.averageMissingValue(silttotal_h(), silttotal_l(), silttotal_r()));
sandvc_r(SoilUtils.averageMissingValue(sandvc_h(), sandvc_l(), sandvc_r(), 0));
sandco_r(SoilUtils.averageMissingValue(sandco_h(), sandco_l(), sandco_r(), 0));
sandmed_r(SoilUtils.averageMissingValue(sandmed_h(), sandmed_l(), sandmed_r(), 0));
sandfine_r(SoilUtils.averageMissingValue(sandfine_h(), sandfine_l(), sandfine_r(), 0));
sandvf_r(SoilUtils.averageMissingValue(sandvf_h(), sandvf_l(), sandvf_r()));
dbthirdbar_r(SoilUtils.averageMissingValue(dbthirdbar_h(), dbthirdbar_l(), dbthirdbar_r()));
wthirdbar_r(SoilUtils.averageMissingValue(wthirdbar_h(), wthirdbar_l(), wthirdbar_r()));
wfifteenbar_r(SoilUtils.averageMissingValue(wfifteenbar_h(), wfifteenbar_l(), wfifteenbar_r()));
ksat_r(SoilUtils.averageMissingValue(ksat_h(), ksat_l(), ksat_r()));
cec7_r(SoilUtils.averageMissingValue(cec7_h(), cec7_l(), cec7_r()));
ecec_r(SoilUtils.averageMissingValue(ecec_h(), ecec_l(), ecec_r()));
om_r(SoilUtils.averageMissingValue(om_h(), om_l(), om_r()));
caco3_r(SoilUtils.averageMissingValue(caco3_h(), caco3_l(), caco3_r()));
ph1to1h2o_r(SoilUtils.averageMissingValue(ph1to1h2o_h(), ph1to1h2o_l(), ph1to1h2o_r()));
ph01mcacl2_r(SoilUtils.averageMissingValue(ph01mcacl2_h(), ph01mcacl2_l(), ph01mcacl2_r()));
lep_r(SoilUtils.averageMissingValue(lep_h(), lep_l(), lep_r()));
if (EvalResult.testDefaultDouble(hzdept_r())) {
errorMessage += " hzdept_r is empty";
}
if (EvalResult.testDefaultDouble(hzdepb_r())) {
errorMessage += " hzdepb_r is empty";
}
if (EvalResult.testDefaultDouble(claytotal_r())) {
errorMessage += " claytotal_r is empty";
}
if (EvalResult.testDefaultDouble(sandtotal_r())) {
errorMessage += " sandtotal_r is empty";
}
if (EvalResult.testDefaultDouble(sandvf_r())) {
errorMessage += " sandvf_r is empty";
}
if (EvalResult.testDefaultDouble(dbthirdbar_r())) {
errorMessage += " dbthirdbar_r is empty";
}
// if (EvalResult.testDefaultDouble(silttotal_r())) {
// errorMessage += " silttotal_r is empty";
// }
// if (EvalResult.testDefaultDouble(sandvc_r())) {
// errorMessage += " sandvc_r is empty";
// }
// if (EvalResult.testDefaultDouble(sandco_r())) {
// errorMessage += " sandco_r is empty";
// }
// if (EvalResult.testDefaultDouble(sandmed_r())) {
// errorMessage += " sandmed_r is empty";
// }
// if (EvalResult.testDefaultDouble(sandfine_r())) {
// errorMessage += " sandfine_r is empty";
// }
// if (EvalResult.testDefaultDouble(wthirdbar_r())) {
// errorMessage += " wthirdbar_r is empty";
// }
// if (EvalResult.testDefaultDouble(wfifteenbar_r())) {
// errorMessage += " wfifteenbar_r is empty";
// }
// if (EvalResult.testDefaultDouble(ksat_r())) {
// errorMessage += " hzksat_rdept_r is empty";
// }
if (EvalResult.testDefaultDouble(cec7_r())) {
if (EvalResult.testDefaultDouble(ecec_r())) {
errorMessage += " cec7_r is empty";
errorMessage += " ecec_r is empty";
} else {
cec7_r(ecec_r());
}
}
if (EvalResult.testDefaultDouble(ph1to1h2o_r())) {
if (EvalResult.testDefaultDouble(ph01mcacl2_r())) {
errorMessage += " ph1to1h2o_r is empty";
errorMessage += " ph01mcacl2_r is empty";
} else {
ph1to1h2o_r(ph01mcacl2_r());
}
}
if (EvalResult.testDefaultDouble(om_r())) {
errorMessage += " om_r is empty";
}
if (EvalResult.testDefaultDouble(caco3_r())) {
errorMessage += " caco3_r is empty";
}
return errorMessage;
}
protected String testWEPP() {
String errorMessage = "";
try {
setWEPPDefaults();
} catch (WEPPException | SDMException ex) {
errorMessage += ex.getMessage();
}
if (EvalResult.testDefaultDouble(sandtotal_r())
|| EvalResult.testDefaultDouble(claytotal_r())
|| EvalResult.testDefaultDouble(cec7_r())
|| EvalResult.testDefaultDouble(sandvf_r())
|| EvalResult.testDefaultDouble(om_r())) {
if (EvalResult.testDefaultDouble(sandtotal_r())) {
errorMessage += " sandtotal_r";
}
if (EvalResult.testDefaultDouble(claytotal_r())) {
errorMessage += " claytotal_r";
}
if (EvalResult.testDefaultDouble(cec7_r())) {
errorMessage += " cec7_r";
}
if (EvalResult.testDefaultDouble(sandvf_r())) {
errorMessage += " sandvf_r";
}
if (EvalResult.testDefaultDouble(om_r())) {
errorMessage += " om_r";
}
}
return errorMessage;
}
public boolean isRestrictingPermiable() throws SDMException {
return (evaluateForRestrictingHorizon() && permiable);
}
public boolean isRestrictingNonPermiable() throws SDMException {
return (evaluateForRestrictingHorizon() && !permiable);
}
public void useGenericHz1Values(boolean value) {
useGenericHz1Values = value;
if (value) {
useGenericHz2Values = false;
}
}
public void useGenericHz2Values(boolean value) {
useGenericHz2Values = value;
if (value) {
useGenericHz1Values = false;
}
}
public final void silttotal_l(double value) {
tableHorizon.silttotal_l(value);
}
public final double silttotal_l() {
return tableHorizon.silttotal_l();
}
public final void claytotal_l(double value) {
tableHorizon.claytotal_l(value);
}
public final double claytotal_l() {
return tableHorizon.claytotal_l();
}
public final void silttotal_h(double value) {
tableHorizon.silttotal_h(value);
}
public final double silttotal_h() {
return tableHorizon.silttotal_h();
}
public final void claytotal_h(double value) {
tableHorizon.claytotal_h(value);
}
public final double claytotal_h() {
return tableHorizon.claytotal_h();
}
public final void sandtotal_l(double value) {
tableHorizon.sandtotal_l(value);
}
public final double sandtotal_l() {
return tableHorizon.sandtotal_l();
}
public final void sandtotal_h(double value) {
tableHorizon.sandtotal_h(value);
}
public final double sandtotal_h() {
return tableHorizon.sandtotal_h();
}
public final void om_l(double value) {
tableHorizon.om_l(value);
}
public final double om_l() {
return tableHorizon.om_l();
}
public final void om_h(double value) {
tableHorizon.om_h(value);
}
public final double om_h() {
return tableHorizon.om_h();
}
public final void cokey(String value) {
tableHorizon.cokey(value);
}
public final String cokey() {
return tableHorizon.cokey();
}
public boolean chkWEPSStopTexture() throws SDMException {
String tmp = getRepresentativeTextureName().toLowerCase();
if (null != tmp) {
for (String textureChk1 : TEXTURE_CHK) {
if (tmp.contains(textureChk1)) {
int tdx = tmp.indexOf(textureChk1); // check if token
if (tdx > 0) {
if (!Character.isWhitespace(tmp.charAt(tdx - 1))) {
continue;
}
if (tmp.charAt(tdx - 1) != '-') {
continue;
}
}
if (tdx + textureChk1.length() < tmp.length()) {
if (!Character.isWhitespace(tmp.charAt(tdx + textureChk1.length()))) {
continue;
}
}
return true;
}
}
}
return false;
}
public void setWEPSDefaults(boolean estimateNulls) {
double calculatedSiltTotal;
hzdept_r(SoilUtils.testNumericSoilElement(999, 0, hzdept_r(), Double.NaN));
hzdepb_r(SoilUtils.testNumericSoilElement(999, 0, hzdepb_r(), Double.NaN));
claytotal_r(SoilUtils.testNumericSoilElement(100, 0, claytotal_r(), Double.NaN));
sandtotal_r(SoilUtils.testNumericSoilElement(100, 0, sandtotal_r(), Double.NaN));
calculatedSiltTotal = 100 - (claytotal_r() + sandtotal_r());
silttotal_r(SoilUtils.testNumericSoilElement(calculatedSiltTotal * 1.001, calculatedSiltTotal * .999, silttotal_r(), calculatedSiltTotal));
sandvf_r(SoilUtils.testNumericSoilElement(100, 0, sandvf_r(), Double.NaN));
dbthirdbar_r(SoilUtils.testNumericSoilElement(2.60, .02, dbthirdbar_r(), Double.NaN));
wthirdbar_r(SoilUtils.testNumericSoilElement(80, 0, wthirdbar_r(), Double.NaN));
om_r(SoilUtils.testNumericSoilElement(100, 0, om_r(), Double.NaN));
caco3_r(SoilUtils.testNumericSoilElement(110, 0, caco3_r(), Double.NaN));
if (estimateNulls) {
ksat_r(SoilUtils.testNumericSoilElement(705, 0, ksat_r(), Double.NaN));
wfifteenbar_r(SoilUtils.testNumericSoilElement(70, 0, wfifteenbar_r(), Double.NaN));
}
}
public void setWEPPDefaults() throws WEPPException, SDMException {
if (EvalResult.testDefaultDouble(cec7_r())) {
if (!EvalResult.testDefaultDouble(ecec_r())) {
cec7_r(ecec_r());
} else {
if (surface) {
throw new WEPPException("WEPP Defaults: No data for CEC nor ECEC available for this horizon, " + chkey() + ". Please contact your SDM data steward to have this corrected.");
} else {
cec7_r(0.0);
}
}
}
if (0.0 == cec7_r()) {
if (surface) {
throw new WEPPException("WEPP Defaults: No valid CEC nor ECEC value greater than 0 available for this surface horizon, " + chkey() + ". Please contact your SDM data steward to have this corrected.");
}
}
if (EvalResult.testDefaultDouble(claytotal_r())) {
claytotal_r(0.0);
}
if (isOrganic()) {
if (this.hzdept_r() <= 40) { // Use Hz1 line from default organic .sol file.
sandtotal_r(50);
claytotal_r(10);
om_r(77);
cec7_r(40);
} else { // Use Hz2 line from default organic .sol file.
sandtotal_r(13);
claytotal_r(5);
om_r(81);
cec7_r(45);
}
fragvol_r(0);
fragments.clear(); // Remove the fragment records, this will set the getWEPPRockFragments() value to be 0.
}
}
public void computeErodibility() throws WEPPException {
if (!EvalResult.testDefaultDouble(sandtotal_r())
&& !EvalResult.testDefaultDouble(claytotal_r())
&& !EvalResult.testDefaultDouble(cec7_r())
&& !EvalResult.testDefaultDouble(sandvf_r())
&& !EvalResult.testDefaultDouble(om_r())) {
if ((sandtotal_r() > 0) && (claytotal_r() > 0) && (cec7_r() > 0)) {
if (claytotal_r() <= 40) {
if (cec7_r() > 1) {
conductivity = -0.265 + 0.0086 * Math.pow(sandtotal_r(), 1.8) + 11.46 * Math.pow(cec7_r(), -0.75);
} else {
conductivity = 11.195 + 0.0086 * Math.pow(sandtotal_r(), 1.8); // from WEPP code, not in documentation
}
} else {
conductivity = 0.0066 * Math.exp(244.0 / claytotal_r());
}
} else {
conductivity = 0; // let model calc
}
if ((sandtotal_r() > 0) && (sandvf_r() > 0) && (om_r() > 0) && (claytotal_r() > 0)) {
if (sandtotal_r() >= 30) {
if (sandvf_r() > 40) {
sandvf_r(40);
}
if (om_r() < 0.35) {
om_r(0.35);
}
if (claytotal_r() > 40) {
claytotal_r(40);
}
interrill = 2728000 + 192100 * sandvf_r();
rill = 0.00197 + 0.00030 * sandvf_r() + 0.03863 * Math.exp(-1.84 * om_r());
shear = 2.67 + 0.065 * claytotal_r() - 0.058 * sandvf_r();
} else {
if (claytotal_r() < 10) {
claytotal_r(10);
}
interrill = 6054000 - 55130 * claytotal_r();
rill = 0.0069 + 0.134 * Math.exp(-0.20 * claytotal_r());
shear = 3.5;
}
} else {
interrill = 0;
rill = 0;
shear = 0;
}
} else {
String missingColumn = "";
if (EvalResult.testDefaultDouble(sandtotal_r())) {
missingColumn += " sandtotal_r";
}
if (EvalResult.testDefaultDouble(claytotal_r())) {
missingColumn += " claytotal_r";
}
if (EvalResult.testDefaultDouble(cec7_r())) {
missingColumn += " cec7_r";
}
if (EvalResult.testDefaultDouble(sandvf_r())) {
missingColumn += " sandvf_r";
}
if (EvalResult.testDefaultDouble(om_r())) {
missingColumn += " om_r";
}
throw new WEPPException("WEPP Computing Erodability: Missing data in column(s): " + missingColumn + ", in the database for this horizon. Cannot compute erodabilty. Contact the SMD data steward to have this corrected for horizon: " + this.chkey());
}
}
public final void cec7_l(double value) {
tableHorizon.cec7_l(value);
}
public final double cec7_l() {
return tableHorizon.cec7_l();
}
public final void cec7_r(double value) {
tableHorizon.cec7_r(value);
}
public final double cec7_r() {
return tableHorizon.cec7_r();
}
public final void cec7_h(double value) {
tableHorizon.cec7_h(value);
}
public final double cec7_h() {
return tableHorizon.cec7_h();
}
public final void wthirdbar_l(double value) {
tableHorizon.wthirdbar_l(value);
}
public final double wthirdbar_l() {
return tableHorizon.wthirdbar_l();
}
public final void wthirdbar_r(double value) {
tableHorizon.wthirdbar_r(value);
}
public final double wthirdbar_r() {
return tableHorizon.wthirdbar_r();
}
public final void wthirdbar_h(double value) {
tableHorizon.wthirdbar_h(value);
}
public final double wthirdbar_h() {
return tableHorizon.wthirdbar_h();
}
public final void wfifteenbar_l(double value) {
tableHorizon.wfifteenbar_l(value);
}
public final double wfifteenbar_l() {
return tableHorizon.wfifteenbar_l();
}
public final void wfifteenbar_r(double value) {
tableHorizon.wfifteenbar_r(value);
}
public final double wfifteenbar_r() {
return tableHorizon.wfifteenbar_r();
}
public final void wfifteenbar_h(double value) {
tableHorizon.wfifteenbar_h(value);
}
public final double wfifteenbar_h() {
return tableHorizon.wfifteenbar_h();
}
public final void dbthirdbar_l(double value) {
tableHorizon.dbthirdbar_l(value);
}
public final double dbthirdbar_l() {
return tableHorizon.dbthirdbar_l();
}
public final void dbthirdbar_r(double value) {
tableHorizon.dbthirdbar_r(value);
}
public final double dbthirdbar_r() {
return tableHorizon.dbthirdbar_r();
}
public final void dbthirdbar_h(double value) {
tableHorizon.dbthirdbar_h(value);
}
public final double dbthirdbar_h() {
return tableHorizon.dbthirdbar_h();
}
public final void silttotal_r(double value) {
tableHorizon.silttotal_r(value);
}
public final double silttotal_r() {
return tableHorizon.silttotal_r();
}
public final void claytotal_r(double value) {
tableHorizon.claytotal_r(value);
}
public final double claytotal_r() {
return tableHorizon.claytotal_r();
}
public final void ph1to1h2o_l(double value) {
tableHorizon.ph1to1h2o_l(value);
}
public final double ph1to1h2o_l() {
return tableHorizon.ph1to1h2o_l();
}
public final void ph1to1h2o_r(double value) {
tableHorizon.ph1to1h2o_r(value);
}
public final double ph1to1h2o_r() {
return tableHorizon.ph1to1h2o_r();
}
public final void ph1to1h2o_h(double value) {
tableHorizon.ph1to1h2o_h(value);
}
public final double ph1to1h2o_h() {
return tableHorizon.ph1to1h2o_h();
}
public String chkey() {
return tableHorizon.chkey();
}
public void chkey(String chkey) {
tableHorizon.chkey(chkey);
}
public void fragvol_r(double value) {
tableHorizonCalculations.fragvol_r(value);
}
public double fragvol_r() {
if (EvalResult.testDefaultDouble(tableHorizonCalculations.fragvol_r())) {
double totalFragvol = 0.0;
for (Fragments tFragment : fragments.values()) {
totalFragvol += tFragment.fragvol_r();
}
fragvol_r((totalFragvol > 100) ? 100.0 : totalFragvol);
}
return tableHorizonCalculations.fragvol_r();
}
public void setOutputColumns(List<String> usedList) {
tableHorizon.setOutputColumns(usedList);
tableHorizonCalculations.setOutputColumns(usedList);
}
public void setOutputColumnOrdering(List<String> usedList) {
tableHorizon.setOutputColumnOrdering(usedList);
tableHorizonCalculations.setOutputColumnOrdering(usedList);
}
public String getRepresentativeTextureName() throws SDMException {
if (null != textureGroups) {
for (TextureGroup t : textureGroups.values()) {
if (t.rvindicator()) {
return t.texture();
}
}
}
throw new SDMException("No representative texture record was found for this horizon, " + chkey() + ". Please notify your SDM data steward of the missing or incorrect data.");
}
public TableHorizon getTableHorizon() {
return tableHorizon;
}
public double getConductivity() {
return conductivity;
}
public double getInterrill() {
return interrill;
}
public double getRill() {
return rill;
}
public double getShear() {
return shear;
}
public TableHorizonCalculations getTableHorizonCalculations() {
return tableHorizonCalculations;
}
public double getWEPPRockFragments() {
double rockFrag = 0.0;
for (Fragments f : fragments.values()) {
rockFrag += SoilUtils.averageMissingValue(f.fragvol_h(), f.fragvol_l(), f.fragvol_r());
}
rockFrag = rockFrag / 100.0;
return rockFrag;
}
public void setUsedColumns(List<String> usedList) {
tableHorizon.setUsedColumns(usedList);
tableHorizonCalculations.setUsedColumns(usedList);
}
/**
*
* @param usedList
*/
public void setTextureGroupOutputColumns(List<String> usedList) {
for (String key : textureGroups.keySet()) {
textureGroups.get(key).setOutputColumns(usedList);
}
}
/**
*
* @param usedList
*/
public void setTextureGroupUsedColumns(List<String> usedList) {
for (String key : textureGroups.keySet()) {
textureGroups.get(key).setUsedColumns(usedList);
}
}
public boolean hasSelectedReason(String reason) {
return selectedReason.contains(reason);
}
public double hzdepb_r() {
return tableHorizon.hzdepb_r();
}
public void hzdepb_r(double value) {
tableHorizon.hzdepb_r(value);
hzdepb_r_in(value * 0.3937);
}
public double hzdept_r() {
return tableHorizon.hzdept_r();
}
public void hzdept_r(double value) {
tableHorizon.hzdept_r(value);
hzdept_r_in(value * 0.3937);
}
public void hzdepb_r_in(double value) {
tableHorizonCalculations.hzdepb_r_in(value);
}
public double hzdepb_r_in() {
if (EvalResult.testDefaultDouble(tableHorizonCalculations.hzdepb_r_in())) {
hzdepb_r_in(hzdepb_r() * 0.3937);
}
return tableHorizonCalculations.hzdepb_r_in();
}
public void hzdept_r_in(double value) {
tableHorizonCalculations.hzdept_r_in(value);
}
public double hzdept_r_in() {
if (EvalResult.testDefaultDouble(tableHorizonCalculations.hzdept_r_in())) {
hzdept_r_in(hzdept_r() * 0.3937);
}
return tableHorizonCalculations.hzdept_r_in();
}
public double hzthk_r() {
if (EvalResult.testDefaultDouble(tableHorizon.hzthk_r())) {
if (!EvalResult.testDefaultDouble(tableHorizon.hzdept_r()) && !EvalResult.testDefaultDouble(tableHorizon.hzdepb_r())) {
hzthk_r(tableHorizon.hzdepb_r() - tableHorizon.hzdept_r());
}
}
return tableHorizon.hzthk_r();
}
public void hzthk_r(double value) {
tableHorizon.hzthk_r(value);
}
public boolean isSurface() {
return surface;
}
protected Boolean evaluateMineral() throws SDMException {
boolean ret_val = false;
if (!EvalResult.testDefaultDouble(om_r())) {
if (om_r() < 15) {
ret_val = true;
} else {
ret_val = false;
}
} else {
ret_val = !isOrganic();
}
return ret_val;
}
public boolean isMineral() throws SDMException {
if (null == mineral) {
mineral = evaluateMineral();
}
return mineral;
}
public void setSurface(boolean value) {
surface = value;
}
public boolean isIgnored() throws SDMException {
String texStr = getRepresentativeTextureName();
for (int i = 0; i < nonCementedRestrictingLayers.size(); i++) {
if (texStr.equalsIgnoreCase(nonCementedRestrictingLayers.get(i))) {
return true;
}
}
for (int i = 0; i < ignoredTextureIfNotSurface.size(); i++) {
if (texStr.equalsIgnoreCase(ignoredTextureIfNotSurface.get(i))) {
if (hzdept_r() > 0) {
return true;
}
}
}
return false;
}
public boolean isPermiable() {
return permiable;
}
public boolean isOrganic() throws SDMException {
if ((om_r() >= 15) || (this.hzname().startsWith("O"))) {// TODO: Review the "Seybold document" to find other tests to run for this.
return true;
}
String texStr = getRepresentativeTextureName().toLowerCase();
if ((null != texStr) && !texStr.isEmpty()) {
for (int i = 0; i < organicTextures.size(); i++) {
if (organicTextures.get(i).equalsIgnoreCase(texStr)) {
return true;
}
}
}
return false;
}
public boolean evaluateForRestrictingHorizon() throws SDMException {
restricting = false;
permiable = false;
String texStr = getRepresentativeTextureName().toLowerCase();
if (texStr.startsWith("Cr")) {
restricting = true;
permiable = true;
}
if (texStr.startsWith("R")) {
restricting = true;
permiable = false;
}
for (int i = 0; i < nonCementedRestrictingLayers.size(); i++) {
if (texStr.equalsIgnoreCase(nonCementedRestrictingLayers.get(i))) {
restricting = true;
permiable = true;
break;
}
}
for (int i = 0; i < restrictingTextures.size(); i++) {
if (texStr.equalsIgnoreCase(restrictingTextures.get(i))) {
restricting = true;
permiable = false;
break;
}
}
for (int i = 0; i < restrictingTexturesPartialMatches.size(); i++) {
String testStr = restrictingTexturesPartialMatches.get(i);
if (texStr.contains(testStr.toUpperCase()) || texStr.contains(testStr.toLowerCase())) {
restricting = true;
permiable = false;
break;
}
}
return restricting;
}
public boolean isRestricting() {
return restricting;
}
public void isRestricting(boolean value) {
restricting = value;
}
public void setRestricting(boolean value) {
restricting = value;
}
public double kffact() {
return tableHorizon.kffact();
}
public void kffact(double value) {
tableHorizon.kffact(value);
}
public double kwfact() {
return tableHorizon.kwfact();
}
public void kwfact(double value) {
tableHorizon.kwfact(value);
}
public void lsfact(double value) {
tableHorizonCalculations.lsfact(value);
}
public double lsfact() {
return tableHorizonCalculations.lsfact();
}
public void merge(Horizon mergeThisUnit) throws ServiceException {
this.tableHorizon.merge(mergeThisUnit.getTableHorizon());
this.tableHorizonCalculations.merge(mergeThisUnit.getTableHorizonCalculations());
for (String key : mergeThisUnit.textureGroups.keySet()) {
if (textureGroups.containsKey(key)) {
textureGroups.get(key).merge(mergeThisUnit.textureGroups().get(key));
}
}
}
public double om_r() {
return tableHorizon.om_r();
}
public void om_r(double value) {
tableHorizon.om_r(value);
}
public double sandtotal_r() {
return tableHorizon.sandtotal_r();
}
public void sandtotal_r(double value) {
tableHorizon.sandtotal_r(value);
}
public boolean selected() {
return selected;
}
public void selected(boolean value) {
selected = value;
}
public void selectedReason(String reason) {
selectedReason.add(reason);
}
/* This is a component level value
public double slopelenusle_r() {
return tableHorizon.slopelenusle_r();
}
public void slopelenusle_r(double value) {
tableHorizon.slopelenusle_r(value);
}
*/
/**
*
* @return @throws JSONException
*/
public JSONArray toJSON() throws JSONException {
JSONArray ret_val = new JSONArray();
JSONArray texturesArray = new JSONArray();
JSONArray fragmentArray = new JSONArray();
tableHorizon.toJSON(ret_val);
tableHorizonCalculations.toJSON(ret_val);
for (Fragments tFragments : this.fragments.values()) {
fragmentArray.put(tFragments.toJSON());
}
for (TextureGroup textureGroup : this.textureGroups.values()) {
if (textureGroup.rvindicator()) {
texturesArray.put(textureGroup.toJSON());
}
}
if (((fragmentArray.length() > 0) && (fragmentArray.getJSONArray(0).length() > 0)) && (ret_val.length() > 0)) {
ret_val.put(JSONUtils.data(FRAGMENTS_LIST, fragmentArray));
}
if (((texturesArray.length() > 0) && (texturesArray.getJSONArray(0).length() > 0)) && (ret_val.length() > 0)) {
ret_val.put(JSONUtils.data(TEXTURE_GROUP_LIST, texturesArray));
}
return ret_val;
}
/**
*
* @return @throws JSONException
*/
public JSONObject toBasicJSON() throws JSONException {
JSONObject ret_val = new JSONObject();
JSONArray texturesArray = new JSONArray();
JSONArray fragmentArray = new JSONArray();
tableHorizon.toBasicJSON(ret_val);
tableHorizonCalculations.toBasicJSON(ret_val);
for (Fragments tFragments : this.fragments.values()) {
fragmentArray.put(tFragments.toBasicJSON());
}
for (TextureGroup textureGroup : this.textureGroups.values()) {
if (textureGroup.rvindicator()) {
texturesArray.put(textureGroup.toBasicJSON());
}
}
if ((fragmentArray.length() > 0) && (ret_val.length() > 0)) {
ret_val.put(FRAGMENTS_LIST, fragmentArray);
}
if ((texturesArray.length() > 0) && (ret_val.length() > 0)) {
ret_val.put(TEXTURE_GROUP_LIST, texturesArray);
}
return ret_val;
}
public boolean isEqual(Horizon thorizon) throws ServiceException {
boolean ret_val = (textureGroups.size() == thorizon.textureGroups().size()
&& fragments.size() == thorizon.fragments.size());
if (ret_val && (tableHorizon.isEqual(thorizon.tableHorizon) && tableHorizonCalculations.isEqual(thorizon.tableHorizonCalculations))) {
for (Fragments tfragment : fragments.values()) {
if (ret_val && thorizon.fragments.containsKey(tfragment.chfragskey())) {
ret_val &= tfragment.isEqual(thorizon.fragments.get(tfragment.chfragskey()));
}
}
for (TextureGroup tgroup : textureGroups.values()) {
if (ret_val && thorizon.textureGroups.containsKey(tgroup.chtgkey())) {
ret_val &= tgroup.isEqual(thorizon.textureGroups.get(tgroup.chtgkey()));
}
}
}
return ret_val;
}
/**
*
*/
public static class HFrags {
public String chfragskey;
public double fragvol_r;
public double fragvol_l;
public double fragvol_h;
public String fragkind;
public double fragsize_l;
public double fragsize_r;
public double fragsize_h;
public String fragshp;
public String fraground;
public String fraghard;
HFrags() {
}
}
}