if (unit == null) unit = "";
v.addAttribute(new Attribute("units", unit));
v.addAttribute(new Attribute("long_name", makeLongName()));
if (firstRecord instanceof GribGridRecord) {
GribGridRecord ggr = (GribGridRecord) firstRecord;
if (ggr.isInterval()) {
CF.CellMethods cm = CF.CellMethods.convertGribCodeTable4_10(ggr.getStatisticalProcessType());
if (cm != null)
v.addAttribute(new Attribute("cell_methods", tcs.getName() + ": " + cm.toString()));
}
}
v.addAttribute(new Attribute("missing_value", new Float(lookup.getFirstMissingValue())));
if (!hcs.isLatLon()) {
if (ucar.nc2.iosp.grib.GribGridServiceProvider.addLatLon)
v.addAttribute(new Attribute("coordinates", "lat lon"));
v.addAttribute(new Attribute("grid_mapping", hcs.getGridName()));
}
// LOOK VECTOR_COMPONENT_FLAG handling is very lame
int icf = hcs.getGds().getInt(GridDefRecord.VECTOR_COMPONENT_FLAG);
String flag;
if (icf == 0) {
flag = Grib2Tables.VectorComponentFlag.easterlyNortherlyRelative.toString();
} else {
flag = Grib2Tables.VectorComponentFlag.gridRelative.toString();
}
if (lookup instanceof Grib2GridTableLookup) {
Grib2GridTableLookup g2lookup = (Grib2GridTableLookup) lookup;
GribGridRecord ggr = (GribGridRecord) firstRecord;
Grib2Pds pds2 = (Grib2Pds) ggr.getPds();
int[] paramId = g2lookup.getParameterId(firstRecord);
v.addAttribute(new Attribute("GRIB_param_discipline", lookup.getDisciplineName(firstRecord)));
v.addAttribute(new Attribute("GRIB_param_category", lookup.getCategoryName(firstRecord)));
v.addAttribute(new Attribute("GRIB_param_name", param.getName()));
v.addAttribute(new Attribute("GRIB_generating_process_type", g2lookup.getGenProcessTypeName(firstRecord)));
v.addAttribute(new Attribute("GRIB_param_id", Array.factory(int.class, new int[]{paramId.length}, paramId)));
v.addAttribute(new Attribute("GRIB_product_definition_template", pds2.getProductDefinitionTemplate()));
v.addAttribute(new Attribute("GRIB_product_definition_template_desc", Grib2Tables.codeTable4_0( pds2.getProductDefinitionTemplate())));
v.addAttribute(new Attribute("GRIB_level_type", new Integer(pds2.getLevelType1())));
v.addAttribute(new Attribute("GRIB_level_type_name", lookup.getLevelName(firstRecord)));
if (pds2.isInterval())
v.addAttribute(new Attribute("GRIB_interval_stat_type", ggr.getStatisticalProcessTypeName() ));
if (pds2.isEnsembleDerived()) {
Grib2Pds.PdsEnsembleDerived pdsDerived = (Grib2Pds.PdsEnsembleDerived) pds2;
v.addAttribute(new Attribute("GRIB_ensemble_derived_type", new Integer(pdsDerived.getDerivedForecastType()) ));
}
if (pds2.isEnsemble())
v.addAttribute(new Attribute("GRIB_ensemble", "true"));
if (pds2.isProbability()) {
Grib2Pds.PdsProbability pdsProb = (Grib2Pds.PdsProbability) pds2;
v.addAttribute(new Attribute("GRIB_probability_type", new Integer(pdsProb.getProbabilityType()) ));
v.addAttribute(new Attribute("GRIB_probability_lower_limit", new Double(pdsProb.getProbabilityLowerLimit()) ));
v.addAttribute(new Attribute("GRIB_probability_upper_limit", new Double(pdsProb.getProbabilityUpperLimit()) ));
}
v.addAttribute(new Attribute("GRIB_" + GridDefRecord.VECTOR_COMPONENT_FLAG, flag));
} else if (lookup instanceof Grib1GridTableLookup) {
Grib1GridTableLookup g1lookup = (Grib1GridTableLookup) lookup;
int[] paramId = g1lookup.getParameterId(firstRecord);
v.addAttribute(new Attribute("GRIB_param_name", param.getDescription()));
v.addAttribute(new Attribute("GRIB_param_short_name", param.getName()));
v.addAttribute(new Attribute("GRIB_center_id", new Integer(paramId[1])));
v.addAttribute(new Attribute("GRIB_table_id", new Integer(paramId[2])));
v.addAttribute(new Attribute("GRIB_param_number", new Integer(paramId[3])));
v.addAttribute(new Attribute("GRIB_param_id", Array.factory(int.class, new int[]{paramId.length}, paramId)));
v.addAttribute(new Attribute("GRIB_product_definition_type", g1lookup.getProductDefinitionName(firstRecord)));
v.addAttribute(new Attribute("GRIB_level_type", new Integer(firstRecord.getLevelType1())));
v.addAttribute(new Attribute("GRIB_" + GridDefRecord.VECTOR_COMPONENT_FLAG, flag));
} else {
v.addAttribute(new Attribute(GridDefRecord.VECTOR_COMPONENT_FLAG, flag));
}
v.setSPobject(this);
int nrecs = ntimes * nlevels;
if (hasEnsemble()) nrecs *= ecs.getNEnsembles();
recordTracker = new GridRecord[nrecs];
if (log.isDebugEnabled()) log.debug("Record Assignment for Variable " + getName());
boolean oneSent = false;
for (GridRecord p : records) {
int level = getVertIndex(p);
if (!getVertIsUsed() && (level > 0)) {
log.warn("inconsistent level encoding=" + level);
level = 0; // inconsistent level encoding ??
}
int time = tcs.findIndex(p);
// System.out.println("time="+time+" level="+level);
if (level < 0) {
log.warn("LEVEL NOT FOUND record; level=" + level + " time= "
+ time + " for " + getName() + " file="
+ ncfile.getLocation() + "\n" + " "
+ getVertLevelName() + " (type=" + p.getLevelType1()
+ "," + p.getLevelType2() + ") value="
+ p.getLevel1() + "," + p.getLevel2() + "\n");
getVertIndex(p); // allow breakpoint
continue;
}
if (time < 0) {
log.warn("TIME NOT FOUND record; level=" + level + " time= "
+ time + " for " + getName() + " file="
+ ncfile.getLocation() + "\n" + " validTime= "
+ p.getValidTime() + "\n");
tcs.findIndex(p); // allow breakpoint
continue;
}
int recno;
if (hasEnsemble()) {
GribGridRecord ggr = (GribGridRecord) p; // LOOK assumes GribGridRecord
int ens = ecs.getIndex(ggr);
if (ens < 0) {
int ensNumber = ggr.getPds().getPerturbationNumber();
int ensType = ggr.getPds().getPerturbationType();
log.warn("ENS NOT FOUND record; level=" + level + " time= "+ time +
" for " + getName() + " file="+ ncfile.getLocation() +
"\n ensNumber= "+ ensNumber + " ensType= "+ ensType + "\n");
ecs.getIndex(ggr); // allow breakpoint
continue; // skip
}
recno = ens * (ntimes * nlevels) + (time * nlevels) + level; // order is ens, time, level
if (recno < 0) {
System.out.println("HEY");
ecs.getIndex(ggr);
}
} else {
recno = time * nlevels + level;
}
boolean sentMessage = false;
if (p instanceof GribGridRecord) {
GribGridRecord ggp = (GribGridRecord) p;
if (ggp.getBelongs() != null) {
log.warn("GribGridRecord " + ggp.cdmVariableName(lookup, true, true) + " recno = " + recno + " already belongs to = " + ggp.getBelongs());
}
ggp.setBelongs(new Belongs(recno, this));
if (recordTracker[recno] != null) {
GribGridRecord ggq = (GribGridRecord) recordTracker[recno];
if (compareData) {
if (!compareData(ggq, ggp, raf)) {
log.warn("GridVariable " + vname + " recno = " + recno + " already has in slot = " + ggq.toString()+
" with different data for "+filename);
sentMessage = true;
}
}
}
}
if (recordTracker[recno] == null) {
recordTracker[recno] = p;
if (log.isDebugEnabled()) log.debug(" " + vc.getVariableName() + " (type=" + p.getLevelType1() + "," + p.getLevelType2() + ") value="
+ p.getLevel1() + "," + p.getLevel2());
} else { // already one in that slot
if ((p instanceof GribGridRecord) && !sentMessage && warnOk && !oneSent) {
GribGridRecord gp = (GribGridRecord) p;
GribGridRecord qp = (GribGridRecord) recordTracker[recno];
log.warn("Duplicate record for "+filename + "\n "+gp.toString() + "\n " + qp.toString());
}
if ((!sendAll)) oneSent = true;
recordTracker[recno] = p; // replace it with latest one
}
}