Skip to content

Commit

Permalink
Merge pull request #8348 from NREL/8317_ValidateOutputTableMonthly
Browse files Browse the repository at this point in the history
Fix #8317 - Warn in Output:Table:Monthly when invalid 'Variable or Meter Name' field
  • Loading branch information
mjwitte committed Nov 7, 2020
2 parents 3d26f11 + 15f462b commit 7495909
Show file tree
Hide file tree
Showing 3 changed files with 143 additions and 104 deletions.
151 changes: 47 additions & 104 deletions src/EnergyPlus/OutputProcessor.cc
Original file line number Diff line number Diff line change
Expand Up @@ -6804,14 +6804,10 @@ void UpdateMeterReporting(EnergyPlusData &state)
int NumAlpha;
int NumNumbers;
int IOStat;
std::string::size_type WildCard;
std::string::size_type TestLen(0);
std::string::size_type varnameLen;
int NumReqMeters;
int NumReqMeterFOs;
int Meter;
ReportingFrequency ReportFreq;
bool NeverFound;

static bool ErrorsFound(false); // If errors detected in input

Expand All @@ -6820,6 +6816,29 @@ void UpdateMeterReporting(EnergyPlusData &state)
ErrorsLogged = true;
}

// Helper lambda to locate a meter index from its name. Returns a negative value if not found
auto findMeterIndexFromMeterName = [](std::string const &name) -> int {
// Return a value <= 0 if not found
int meterIndex = -99;

std::string::size_type wildCardPosition = index(name, '*');

if (wildCardPosition == std::string::npos) {
meterIndex = UtilityRoutines::FindItem(name, OutputProcessor::EnergyMeters);
} else { // Wildcard input
for (int Meter = 1; Meter <= OutputProcessor::NumEnergyMeters; ++Meter) {
if (UtilityRoutines::SameString(OutputProcessor::EnergyMeters(Meter).Name.substr(0, wildCardPosition),
name.substr(0, wildCardPosition)))
{
meterIndex = Meter;
break;
}
}
}

return meterIndex;
};

cCurrentModuleObject = "Output:Meter";
NumReqMeters = inputProcessor->getNumObjectsFound(cCurrentModuleObject);

Expand All @@ -6841,33 +6860,14 @@ void UpdateMeterReporting(EnergyPlusData &state)
varnameLen = index(Alphas(1), '[');
if (varnameLen != std::string::npos) Alphas(1).erase(varnameLen);

WildCard = index(Alphas(1), '*');
if (WildCard != std::string::npos) {
TestLen = WildCard;
}

ReportFreq = determineFrequency(Alphas(2));

if (WildCard == std::string::npos) {
Meter = UtilityRoutines::FindItem(Alphas(1), EnergyMeters);
if (Meter == 0) {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
continue;
}

SetInitialMeterReportingAndOutputNames(state, Meter, false, ReportFreq, false);

} else { // Wildcard input
NeverFound = true;
for (Meter = 1; Meter <= NumEnergyMeters; ++Meter) {
if (!UtilityRoutines::SameString(EnergyMeters(Meter).Name.substr(0, TestLen), Alphas(1).substr(0, TestLen))) continue;
NeverFound = false;

SetInitialMeterReportingAndOutputNames(state, Meter, false, ReportFreq, false);
}
if (NeverFound) {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
}
int meterIndex = findMeterIndexFromMeterName(Alphas(1));
if (meterIndex > 0) {
// MeterFileOnlyIndicator is false, CumulativeIndicator is false
SetInitialMeterReportingAndOutputNames(state, meterIndex, false, ReportFreq, false);
} else {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
}
}

Expand All @@ -6891,33 +6891,14 @@ void UpdateMeterReporting(EnergyPlusData &state)
varnameLen = index(Alphas(1), '[');
if (varnameLen != std::string::npos) Alphas(1).erase(varnameLen);

WildCard = index(Alphas(1), '*');
if (WildCard != std::string::npos) {
TestLen = WildCard;
}

ReportFreq = determineFrequency(Alphas(2));

if (WildCard == std::string::npos) {
Meter = UtilityRoutines::FindItem(Alphas(1), EnergyMeters);
if (Meter == 0) {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
continue;
}

SetInitialMeterReportingAndOutputNames(state, Meter, true, ReportFreq, false);

} else { // Wildcard input
NeverFound = true;
for (Meter = 1; Meter <= NumEnergyMeters; ++Meter) {
if (!UtilityRoutines::SameString(EnergyMeters(Meter).Name.substr(0, TestLen), Alphas(1).substr(0, TestLen))) continue;
NeverFound = false;

SetInitialMeterReportingAndOutputNames(state, Meter, true, ReportFreq, false);
}
if (NeverFound) {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
}
int meterIndex = findMeterIndexFromMeterName(Alphas(1));
if (meterIndex > 0) {
// MeterFileOnlyIndicator is true, CumulativeIndicator is false
SetInitialMeterReportingAndOutputNames(state, meterIndex, true, ReportFreq, false);
} else {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
}
}

Expand All @@ -6942,33 +6923,14 @@ void UpdateMeterReporting(EnergyPlusData &state)
varnameLen = index(Alphas(1), '[');
if (varnameLen != std::string::npos) Alphas(1).erase(varnameLen);

WildCard = index(Alphas(1), '*');
if (WildCard != std::string::npos) {
TestLen = WildCard;
}

ReportFreq = determineFrequency(Alphas(2));

if (WildCard == std::string::npos) {
Meter = UtilityRoutines::FindItem(Alphas(1), EnergyMeters);
if (Meter == 0) {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
continue;
}

SetInitialMeterReportingAndOutputNames(state, Meter, false, ReportFreq, true);

} else { // Wildcard input
NeverFound = true;
for (Meter = 1; Meter <= NumEnergyMeters; ++Meter) {
if (!UtilityRoutines::SameString(EnergyMeters(Meter).Name.substr(0, TestLen), Alphas(1).substr(0, TestLen))) continue;
NeverFound = false;

SetInitialMeterReportingAndOutputNames(state, Meter, false, ReportFreq, true);
}
if (NeverFound) {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
}
int meterIndex = findMeterIndexFromMeterName(Alphas(1));
if (meterIndex > 0) {
// MeterFileOnlyIndicator is false, CumulativeIndicator is true
SetInitialMeterReportingAndOutputNames(state, meterIndex, false, ReportFreq, true);
} else {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
}
}

Expand All @@ -6992,33 +6954,14 @@ void UpdateMeterReporting(EnergyPlusData &state)
varnameLen = index(Alphas(1), '[');
if (varnameLen != std::string::npos) Alphas(1).erase(varnameLen);

WildCard = index(Alphas(1), '*');
if (WildCard != std::string::npos) {
TestLen = WildCard;
}

ReportFreq = determineFrequency(Alphas(2));

if (WildCard == std::string::npos) {
Meter = UtilityRoutines::FindItem(Alphas(1), EnergyMeters);
if (Meter == 0) {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
continue;
}

SetInitialMeterReportingAndOutputNames(state, Meter, true, ReportFreq, true);

} else { // Wildcard input
NeverFound = true;
for (Meter = 1; Meter <= NumEnergyMeters; ++Meter) {
if (!UtilityRoutines::SameString(EnergyMeters(Meter).Name.substr(0, TestLen), Alphas(1).substr(0, TestLen))) continue;
NeverFound = false;

SetInitialMeterReportingAndOutputNames(state, Meter, true, ReportFreq, true);
}
if (NeverFound) {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
}
int meterIndex = findMeterIndexFromMeterName(Alphas(1));
if (meterIndex > 0) {
// MeterFileOnlyIndicator is true, CumulativeIndicator is true
SetInitialMeterReportingAndOutputNames(state, meterIndex, true, ReportFreq, true);
} else {
ShowWarningError(cCurrentModuleObject + ": invalid " + cAlphaFieldNames(1) + "=\"" + Alphas(1) + "\" - not found.");
}
}

Expand Down
3 changes: 3 additions & 0 deletions src/EnergyPlus/OutputReportTabular.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1145,6 +1145,9 @@ namespace OutputReportTabular {
curVariMeter = UtilityRoutines::MakeUPPERCase(MonthlyFieldSetInput(FirstColumn + colNum - 1).variMeter);
// call the key count function but only need count during this pass
GetVariableKeyCountandType(state, curVariMeter, KeyCount, TypeVar, AvgSumVar, StepTypeVar, UnitsVar);
if (TypeVar == OutputProcessor::VarType_NotFound) {
ShowWarningError("In Output:Table:Monthly '" + MonthlyInput(TabNum).name + "' invalid Variable or Meter Name '" + curVariMeter + "'");
}
// IF (KeyCount > maxKeyCount) THEN
// DEALLOCATE(NamesOfKeys)
// DEALLOCATE(IndexesForKeyVar)
Expand Down
93 changes: 93 additions & 0 deletions tst/EnergyPlus/unit/OutputReportTabular.unit.cc
Original file line number Diff line number Diff line change
Expand Up @@ -8339,3 +8339,96 @@ TEST_F(EnergyPlusFixture, OutputReportTabular_GatherHeatGainReport)
EXPECT_EQ(1000.0, DataHeatBalance::ZonePreDefRep(1).SHGSAnHvacATUHt);
EXPECT_EQ(-2000.0, DataHeatBalance::ZonePreDefRep(1).SHGSAnHvacATUCl);
}


TEST_F(EnergyPlusFixture, OutputReportTabularMonthly_8317_ValidateOutputTableMonthly)
{
// Test for #8317 - Output:Table:Monthly does not warn about invalid variable or meter name
std::string const idf_objects = delimited_string({

"Schedule:Compact,",
" OnSched, !- Name",
" Fraction, !- Schedule Type Limits Name",
" Through: 12/31, !- Field 1",
" For: AllDays, !- Field 2",
" Until: 24:00, 1.0; !- Field 3",

"ScheduleTypeLimits,",
" Fraction, !- Name",
" 0.0, !- Lower Limit Value",
" 1.0, !- Upper Limit Value",
" CONTINUOUS; !- Numeric Type",

"Output:Table:Monthly,",
" My Report, !- Name",
" 2, !- Digits After Decimal",
" Heating:Gas, !- Variable or Meter 1 Name", // A bad meter name
" SumOrAverage, !- Aggregation Type for Variable or Meter 1",
" Exterior Lights Electric Power, !- Variable or Meter 2 Name", // A bad variable name
" Maximum, !- Aggregation Type for Variable or Meter 2",
" AlwaysOn, !- Variable or Meter 3 Name", // A bad name (eg: Schedule)
" Maximum, !- Aggregation Type for Variable or Meter 3",
" Exterior Lights Electricity Rate, !- Variable or Meter 4 Name", // A good variable name
" Minimum, !- Aggregation Type for Variable or Meter 4",
" OnSched, !- Variable or Meter 5 Name", // A good schedule name
" Minimum, !- Aggregation Type for Variable or Meter 5",
" Heating:NaturalGas, !- Variable or Meter 6 Name", // A good meter name
" SumOrAverage; !- Aggregation Type for Variable or Meter 6",
});

ASSERT_TRUE(process_idf(idf_objects));

Real64 extLitUse;

SetupOutputVariable(state, "Exterior Lights Electricity Energy",
OutputProcessor::Unit::J,
extLitUse,
"Zone",
"Sum",
"Lite1",
_,
"Electricity",
"Exterior Lights",
"General");
SetupOutputVariable(state, "Exterior Lights Electricity Rate",
OutputProcessor::Unit::W,
extLitUse,
"Zone",
"Sum",
"Lite2",
_,
"Electricity",
"Exterior Lights",
"General");

DataGlobals::DoWeathSim = true;
DataGlobals::TimeStepZone = 0.25;
DataGlobals::TimeStepZoneSec = DataGlobals::TimeStepZone * 60.0;

InitializeOutput(state);

int meter_array_ptr = -1;
bool errors_found = false;

std::string resourceType("NaturalGas");
std::string endUse("Heating");
std::string endUseSub("");
std::string group("");
std::string const zoneName("");

AttachMeters(OutputProcessor::Unit::J, resourceType, endUse, endUseSub, group, zoneName, 1, meter_array_ptr, errors_found);

EXPECT_FALSE(errors_found);
EXPECT_EQ(3, meter_array_ptr); // 2 meters were setup via SetupOutputVariable already

OutputReportTabular::GetInputTabularMonthly(state);
OutputReportTabular::InitializeTabularMonthly(state);

std::string expected_error = delimited_string({
" ** Warning ** In Output:Table:Monthly 'MY REPORT' invalid Variable or Meter Name 'HEATING:GAS'",
" ** Warning ** In Output:Table:Monthly 'MY REPORT' invalid Variable or Meter Name 'EXTERIOR LIGHTS ELECTRIC POWER'",
" ** Warning ** In Output:Table:Monthly 'MY REPORT' invalid Variable or Meter Name 'ALWAYSON'",
});

compare_err_stream(expected_error);
}

5 comments on commit 7495909

@nrel-bot-2b
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

develop (mjwitte) - x86_64-Linux-Ubuntu-18.04-gcc-7.5: OK (2296 of 2296 tests passed, 0 test warnings)

Build Badge Test Badge

@nrel-bot-3
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

develop (mjwitte) - x86_64-MacOS-10.15-clang-11.0.0: OK (2276 of 2276 tests passed, 0 test warnings)

Build Badge Test Badge

@nrel-bot-2
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

develop (mjwitte) - x86_64-Linux-Ubuntu-18.04-gcc-7.5-UnitTestsCoverage-Debug: OK (1557 of 1557 tests passed, 0 test warnings)

Build Badge Test Badge Coverage Badge

@nrel-bot
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

develop (mjwitte) - Win64-Windows-10-VisualStudio-16: OK (2248 of 2249 tests passed, 0 test warnings)

Failures:\n

EnergyPlusFixture Test Summary

  • Passed: 1087
  • Failed: 1

Build Badge Test Badge

@nrel-bot-2c
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

develop (mjwitte) - x86_64-Linux-Ubuntu-18.04-gcc-7.5-IntegrationCoverage-Debug: OK (722 of 722 tests passed, 0 test warnings)

Build Badge Test Badge Coverage Badge

Please sign in to comment.