Line data Source code
1 : // EnergyPlus, Copyright (c) 1996-2025, The Board of Trustees of the University of Illinois,
2 : // The Regents of the University of California, through Lawrence Berkeley National Laboratory
3 : // (subject to receipt of any required approvals from the U.S. Dept. of Energy), Oak Ridge
4 : // National Laboratory, managed by UT-Battelle, Alliance for Sustainable Energy, LLC, and other
5 : // contributors. All rights reserved.
6 : //
7 : // NOTICE: This Software was developed under funding from the U.S. Department of Energy and the
8 : // U.S. Government consequently retains certain rights. As such, the U.S. Government has been
9 : // granted for itself and others acting on its behalf a paid-up, nonexclusive, irrevocable,
10 : // worldwide license in the Software to reproduce, distribute copies to the public, prepare
11 : // derivative works, and perform publicly and display publicly, and to permit others to do so.
12 : //
13 : // Redistribution and use in source and binary forms, with or without modification, are permitted
14 : // provided that the following conditions are met:
15 : //
16 : // (1) Redistributions of source code must retain the above copyright notice, this list of
17 : // conditions and the following disclaimer.
18 : //
19 : // (2) Redistributions in binary form must reproduce the above copyright notice, this list of
20 : // conditions and the following disclaimer in the documentation and/or other materials
21 : // provided with the distribution.
22 : //
23 : // (3) Neither the name of the University of California, Lawrence Berkeley National Laboratory,
24 : // the University of Illinois, U.S. Dept. of Energy nor the names of its contributors may be
25 : // used to endorse or promote products derived from this software without specific prior
26 : // written permission.
27 : //
28 : // (4) Use of EnergyPlus(TM) Name. If Licensee (i) distributes the software in stand-alone form
29 : // without changes from the version obtained under this License, or (ii) Licensee makes a
30 : // reference solely to the software portion of its product, Licensee must refer to the
31 : // software as "EnergyPlus version X" software, where "X" is the version number Licensee
32 : // obtained under this License and may not use a different name for the software. Except as
33 : // specifically required in this Section (4), Licensee shall not use in a company name, a
34 : // product name, in advertising, publicity, or other promotional activities any name, trade
35 : // name, trademark, logo, or other designation of "EnergyPlus", "E+", "e+" or confusingly
36 : // similar designation, without the U.S. Department of Energy's prior written consent.
37 : //
38 : // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR
39 : // IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
40 : // AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
41 : // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
42 : // CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
43 : // SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
44 : // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
45 : // OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
46 : // POSSIBILITY OF SUCH DAMAGE.
47 :
48 : // FMI-Related Headers
49 : extern "C" {
50 : #include <FMI/main.h>
51 : }
52 :
53 : // C++ Headers
54 : #include <memory>
55 : #include <string>
56 :
57 : // ObjexxFCL Headers
58 : #include <ObjexxFCL/Array.functions.hh>
59 : #include <ObjexxFCL/Array1D.hh>
60 : #include <ObjexxFCL/environment.hh>
61 : #include <ObjexxFCL/string.functions.hh>
62 :
63 : // EnergyPlus Headers
64 : #include <EnergyPlus/BranchInputManager.hh>
65 : #include <EnergyPlus/BranchNodeConnections.hh>
66 : #include <EnergyPlus/CostEstimateManager.hh>
67 : #include <EnergyPlus/CurveManager.hh>
68 : #include <EnergyPlus/Data/EnergyPlusData.hh>
69 : #include <EnergyPlus/DataAirLoop.hh>
70 : #include <EnergyPlus/DataBranchNodeConnections.hh>
71 : #include <EnergyPlus/DataConvergParams.hh>
72 : #include <EnergyPlus/DataErrorTracking.hh>
73 : #include <EnergyPlus/DataGlobalConstants.hh>
74 : #include <EnergyPlus/DataHVACGlobals.hh>
75 : #include <EnergyPlus/DataHeatBalFanSys.hh>
76 : #include <EnergyPlus/DataHeatBalance.hh>
77 : #include <EnergyPlus/DataIPShortCuts.hh>
78 : #include <EnergyPlus/DataLoopNode.hh>
79 : #include <EnergyPlus/DataOutputs.hh>
80 : #include <EnergyPlus/DataReportingFlags.hh>
81 : #include <EnergyPlus/DataRuntimeLanguage.hh>
82 : #include <EnergyPlus/DataStringGlobals.hh>
83 : #include <EnergyPlus/DataSurfaces.hh>
84 : #include <EnergyPlus/DataSystemVariables.hh>
85 : #include <EnergyPlus/DataZoneEquipment.hh>
86 : #include <EnergyPlus/DemandManager.hh>
87 : #include <EnergyPlus/DisplayRoutines.hh>
88 : #include <EnergyPlus/DualDuct.hh>
89 : #include <EnergyPlus/EMSManager.hh>
90 : #include <EnergyPlus/EconomicLifeCycleCost.hh>
91 : #include <EnergyPlus/EconomicTariff.hh>
92 : #include <EnergyPlus/ElectricPowerServiceManager.hh>
93 : #include <EnergyPlus/ExteriorEnergyUse.hh>
94 : #include <EnergyPlus/ExternalInterface.hh>
95 : #include <EnergyPlus/FaultsManager.hh>
96 : #include <EnergyPlus/FileSystem.hh>
97 : #include <EnergyPlus/FluidProperties.hh>
98 : #include <EnergyPlus/GeneralRoutines.hh>
99 : #include <EnergyPlus/HVACControllers.hh>
100 : #include <EnergyPlus/HVACManager.hh>
101 : #include <EnergyPlus/HVACSizingSimulationManager.hh>
102 : #include <EnergyPlus/HeatBalanceAirManager.hh>
103 : #include <EnergyPlus/HeatBalanceIntRadExchange.hh>
104 : #include <EnergyPlus/HeatBalanceManager.hh>
105 : #include <EnergyPlus/HeatBalanceSurfaceManager.hh>
106 : #include <EnergyPlus/InputProcessing/InputProcessor.hh>
107 : #include <EnergyPlus/MixedAir.hh>
108 : #include <EnergyPlus/NodeInputManager.hh>
109 : #include <EnergyPlus/OutAirNodeManager.hh>
110 : #include <EnergyPlus/OutputProcessor.hh>
111 : #include <EnergyPlus/OutputReportPredefined.hh>
112 : #include <EnergyPlus/OutputReportTabular.hh>
113 : #include <EnergyPlus/OutputReports.hh>
114 : #include <EnergyPlus/Plant/PlantManager.hh>
115 : #include <EnergyPlus/PlantPipingSystemsManager.hh>
116 : #include <EnergyPlus/PluginManager.hh>
117 : #include <EnergyPlus/PollutionModule.hh>
118 : #include <EnergyPlus/Psychrometrics.hh>
119 : #include <EnergyPlus/RefrigeratedCase.hh>
120 : #include <EnergyPlus/ReportCoilSelection.hh>
121 : #include <EnergyPlus/ResultsFramework.hh>
122 : #include <EnergyPlus/SetPointManager.hh>
123 : #include <EnergyPlus/SimulationManager.hh>
124 : #include <EnergyPlus/SizingManager.hh>
125 : #include <EnergyPlus/SolarShading.hh>
126 : #include <EnergyPlus/SurfaceGeometry.hh>
127 : #include <EnergyPlus/SystemReports.hh>
128 : #include <EnergyPlus/UtilityRoutines.hh>
129 : #include <EnergyPlus/WeatherManager.hh>
130 : #include <EnergyPlus/ZoneContaminantPredictorCorrector.hh>
131 : #include <EnergyPlus/ZoneEquipmentManager.hh>
132 : #include <EnergyPlus/ZoneTempPredictorCorrector.hh>
133 : #include <EnergyPlus/api/datatransfer.h>
134 :
135 : namespace EnergyPlus {
136 : namespace SimulationManager {
137 :
138 : // MODULE INFORMATION:
139 : // AUTHOR Rick Strand
140 : // DATE WRITTEN January 1997
141 :
142 : // PURPOSE OF THIS MODULE:
143 : // This module contains the main driver routine which manages the major
144 : // control loops of the EnergyPlus simulation. This module is also
145 : // responsible for setting the global environment flags for these
146 : // loops.
147 :
148 : // METHODOLOGY EMPLOYED:
149 : // This module was constructed from the remnants of (I)BLAST routines
150 : // SIMBLD (Simulate Building), SIMZG (Simulate Zone Group), and SIMZGD
151 : // (Simulate Zone Group for a Day).
152 :
153 : // REFERENCES:
154 : // (I)BLAST legacy code, internal Reverse Engineering documentation,
155 : // and internal Evolutionary Engineering documentation.
156 :
157 : // Using/Aliasing
158 : using namespace DataSizing;
159 : using namespace DataSystemVariables;
160 : using namespace HeatBalanceManager;
161 : using namespace ExternalInterface;
162 :
163 : // MODULE PARAMETER DEFINITIONS:
164 :
165 75 : void ManageSimulation(EnergyPlusData &state)
166 : {
167 :
168 : // SUBROUTINE INFORMATION:
169 : // AUTHOR Rick Strand
170 : // DATE WRITTEN January 1997
171 :
172 : // PURPOSE OF THIS SUBROUTINE:
173 : // This subroutine is the main driver of the simulation manager module.
174 : // It contains the main environment-time loops for the building
175 : // simulation. This includes the environment loop, a day loop, an
176 : // hour loop, and a time step loop.
177 :
178 : // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
179 75 : bool ErrorsFound(false);
180 75 : bool oneTimeUnderwaterBoundaryCheck = true;
181 75 : bool AnyUnderwaterBoundaries = false;
182 :
183 75 : state.files.outputControl.getInput(state);
184 75 : state.dataResultsFramework->resultsFramework->setupOutputOptions(state);
185 :
186 150 : state.files.debug.ensure_open(state, "OpenOutputFiles", state.files.outputControl.dbg);
187 :
188 75 : if (!state.dataSQLiteProcedures->sqlite) {
189 73 : state.dataSQLiteProcedures->sqlite = EnergyPlus::CreateSQLiteDatabase(state);
190 : }
191 :
192 75 : if (state.dataSQLiteProcedures->sqlite) {
193 5 : state.dataSQLiteProcedures->sqlite->sqliteBegin();
194 15 : state.dataSQLiteProcedures->sqlite->createSQLiteSimulationsRecord(
195 10 : 1, state.dataStrGlobals->VerStringVar, state.dataStrGlobals->CurrentDateTime);
196 5 : state.dataSQLiteProcedures->sqlite->sqliteCommit();
197 : }
198 :
199 75 : PostIPProcessing(state);
200 :
201 75 : state.dataGlobal->BeginSimFlag = true;
202 75 : state.dataGlobal->DoOutputReporting = false;
203 75 : state.dataReportFlag->DisplayPerfSimulationFlag = false;
204 75 : state.dataReportFlag->DoWeatherInitReporting = false;
205 75 : state.dataSimulationManager->RunPeriodsInInput =
206 75 : (state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "RunPeriod") > 0 ||
207 75 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "RunPeriod:CustomRange") > 0 || state.dataSysVars->FullAnnualRun);
208 75 : state.dataErrTracking->AskForConnectionsReport = false; // set to false until sizing is finished
209 :
210 75 : state.init_constant_state(state);
211 75 : state.init_state(state);
212 :
213 75 : CheckForMisMatchedEnvironmentSpecifications(state);
214 75 : CheckForRequestedReporting(state);
215 75 : OutputReportPredefined::SetPredefinedTables(state);
216 75 : SetPreConstructionInputParameters(state); // establish array bounds for constructions early
217 :
218 75 : OutputProcessor::SetupTimePointers(
219 75 : state, OutputProcessor::TimeStepType::Zone, state.dataGlobal->TimeStepZone); // Set up Time pointer for HB/Zone Simulation
220 75 : OutputProcessor::SetupTimePointers(state, OutputProcessor::TimeStepType::System, state.dataHVACGlobal->TimeStepSys);
221 :
222 75 : createFacilityElectricPowerServiceObject(state);
223 75 : createCoilSelectionReportObj(state);
224 : // read object information early in simulation
225 75 : isInputObjectUsed(state);
226 :
227 75 : BranchInputManager::ManageBranchInput(state); // just gets input and returns.
228 :
229 : // Create a new plugin manager which starts up the Python interpreter
230 75 : state.dataPluginManager->pluginManager = std::make_unique<EnergyPlus::PluginManagement::PluginManager>(state);
231 :
232 74 : state.dataGlobal->DoingSizing = true;
233 74 : SizingManager::ManageSizing(state);
234 :
235 74 : bool SimsDone = false;
236 74 : if (state.dataGlobal->DoDesDaySim || state.dataGlobal->DoWeathSim || state.dataGlobal->DoHVACSizingSimulation) {
237 66 : state.dataGlobal->DoOutputReporting = true;
238 : }
239 74 : state.dataGlobal->DoingSizing = false;
240 74 : state.dataHeatBal->doSpaceHeatBalance = state.dataHeatBal->doSpaceHeatBalanceSimulation;
241 :
242 108 : if ((state.dataGlobal->DoZoneSizing || state.dataGlobal->DoSystemSizing || state.dataGlobal->DoPlantSizing) &&
243 34 : !(state.dataGlobal->DoDesDaySim || (state.dataGlobal->DoWeathSim && state.dataSimulationManager->RunPeriodsInInput))) {
244 24 : ShowWarningError(state,
245 : "ManageSimulation: Input file has requested Sizing Calculations but no Simulations are requested (in SimulationControl "
246 : "object). Succeeding warnings/errors may be confusing.");
247 : }
248 74 : bool Available = true; // an environment is available to process
249 :
250 74 : if (state.dataGlobal->DoPureLoadCalc) {
251 8 : state.dataGlobal->DoOutputReporting = true;
252 8 : Available = false;
253 8 : state.dataOutRptTab->WriteTabularFiles = true;
254 : }
255 :
256 74 : if (state.dataBranchInputManager->InvalidBranchDefinitions) {
257 0 : ShowFatalError(state, "Preceding error(s) in Branch Input cause termination.");
258 : }
259 :
260 74 : DisplayString(state, "Adjusting Air System Sizing");
261 74 : SizingManager::ManageSystemSizingAdjustments(state);
262 :
263 74 : DisplayString(state, "Adjusting Standard 62.1 Ventilation Sizing");
264 74 : SizingManager::ManageSystemVentilationAdjustments(state);
265 :
266 74 : DisplayString(state, "Initializing Simulation");
267 74 : state.dataGlobal->KickOffSimulation = true;
268 :
269 74 : Weather::ResetEnvironmentCounter(state);
270 74 : SetupSimulation(state, ErrorsFound);
271 :
272 73 : FaultsManager::CheckAndReadFaults(state);
273 :
274 73 : Curve::InitCurveReporting(state);
275 :
276 73 : state.dataErrTracking->AskForConnectionsReport = true; // set to true now that input processing and sizing is done.
277 73 : state.dataGlobal->KickOffSimulation = false;
278 73 : state.dataGlobal->WarmupFlag = false;
279 73 : state.dataReportFlag->DoWeatherInitReporting = true;
280 :
281 : // Note: All the inputs have been 'gotten' by the time we get here.
282 73 : if (state.dataGlobal->DoOutputReporting) {
283 73 : DisplayString(state, "Reporting Surfaces");
284 73 : bool ErrFound = false;
285 73 : bool TerminalError = false;
286 :
287 73 : ReportSurfaces(state);
288 :
289 73 : NodeInputManager::SetupNodeVarsForReporting(state);
290 73 : state.dataGlobal->MetersHaveBeenInitialized = true;
291 73 : Pollution::SetupPollutionMeterReporting(state);
292 73 : SystemReports::AllocateAndSetUpVentReports(state);
293 73 : if (state.dataPluginManager->pluginManager) {
294 73 : EnergyPlus::PluginManagement::PluginManager::setupOutputVariables(state);
295 : }
296 73 : UpdateMeterReporting(state);
297 73 : Pollution::CheckPollutionMeterReporting(state);
298 73 : state.dataElectPwrSvcMgr->facilityElectricServiceObj->verifyCustomMetersElecPowerMgr(state);
299 73 : Pollution::SetupPollutionCalculations(state);
300 73 : DemandManager::InitDemandManagers(state);
301 73 : BranchInputManager::TestBranchIntegrity(state, ErrFound);
302 73 : if (ErrFound) TerminalError = true;
303 73 : TestAirPathIntegrity(state, ErrFound);
304 73 : if (ErrFound) TerminalError = true;
305 73 : NodeInputManager::CheckMarkedNodes(state, ErrFound);
306 73 : if (ErrFound) TerminalError = true;
307 73 : BranchNodeConnections::CheckNodeConnections(state, ErrFound);
308 73 : if (ErrFound) TerminalError = true;
309 73 : BranchNodeConnections::TestCompSetInletOutletNodes(state, ErrFound);
310 73 : if (ErrFound) TerminalError = true;
311 73 : MixedAir::CheckControllerLists(state, ErrFound);
312 73 : if (ErrFound) TerminalError = true;
313 :
314 73 : if (state.dataGlobal->DoDesDaySim || state.dataGlobal->DoWeathSim || state.dataGlobal->DoPureLoadCalc) {
315 73 : ReportLoopConnections(state);
316 73 : SystemReports::ReportAirLoopConnections(state);
317 73 : ReportNodeConnections(state);
318 : }
319 73 : SystemReports::CreateEnergyReportStructure(state);
320 : bool anyEMSRan;
321 : // point to finish setup processing EMS, sensor ready now
322 73 : EMSManager::ManageEMS(state, EMSManager::EMSCallFrom::SetupSimulation, anyEMSRan, ObjexxFCL::Optional_int_const());
323 73 : ProduceRDDMDD(state);
324 :
325 73 : if (TerminalError) {
326 0 : ShowFatalError(state, "Previous Conditions cause program termination.");
327 : }
328 : }
329 :
330 : // up until this point, output vars, meters, actuators, etc., may not have been registered; they are now
331 73 : state.dataPluginManager->fullyReady = true;
332 :
333 73 : if (state.dataSQLiteProcedures->sqlite) {
334 5 : state.dataSQLiteProcedures->sqlite->sqliteBegin();
335 5 : state.dataSQLiteProcedures->sqlite->updateSQLiteSimulationRecord(1, state.dataGlobal->TimeStepsInHour);
336 5 : state.dataSQLiteProcedures->sqlite->sqliteCommit();
337 : }
338 :
339 73 : EconomicLifeCycleCost::GetInputForLifeCycleCost(state); // must be prior to WriteTabularReports -- do here before big simulation stuff.
340 :
341 : // check for variable latitude/location/etc
342 73 : Weather::ReadVariableLocationOrientation(state);
343 :
344 : // if user requested HVAC Sizing Simulation, call HVAC sizing simulation manager
345 73 : if (state.dataGlobal->DoHVACSizingSimulation) {
346 0 : ManageHVACSizingSimulation(state, ErrorsFound);
347 : }
348 :
349 73 : if (!state.dataGlobal->DoPureLoadCalc) {
350 130 : ShowMessage(state, "Beginning Simulation");
351 65 : DisplayString(state, "Beginning Primary Simulation");
352 : }
353 73 : Weather::ResetEnvironmentCounter(state);
354 :
355 73 : int EnvCount = 0;
356 73 : state.dataGlobal->WarmupFlag = true;
357 :
358 202 : while (Available) {
359 258 : if (state.dataGlobal->stopSimulation) break;
360 :
361 193 : Weather::GetNextEnvironment(state, Available, ErrorsFound);
362 :
363 193 : if (!Available) break;
364 129 : if (ErrorsFound) break;
365 146 : if ((!state.dataGlobal->DoDesDaySim) && (state.dataGlobal->KindOfSim != Constant::KindOfSim::RunPeriodWeather)) continue;
366 129 : if ((!state.dataGlobal->DoWeathSim) && (state.dataGlobal->KindOfSim == Constant::KindOfSim::RunPeriodWeather)) continue;
367 112 : if (state.dataGlobal->KindOfSim == Constant::KindOfSim::HVACSizeDesignDay) continue; // don't run these here, only for sizing simulations
368 :
369 112 : if (state.dataGlobal->KindOfSim == Constant::KindOfSim::HVACSizeRunPeriodDesign)
370 0 : continue; // don't run these here, only for sizing simulations
371 :
372 112 : ++EnvCount;
373 :
374 112 : if (state.dataSQLiteProcedures->sqlite) {
375 8 : state.dataSQLiteProcedures->sqlite->sqliteBegin();
376 24 : state.dataSQLiteProcedures->sqlite->createSQLiteEnvironmentPeriodRecord(
377 16 : state.dataEnvrn->CurEnvirNum, state.dataEnvrn->EnvironmentName, state.dataGlobal->KindOfSim);
378 8 : state.dataSQLiteProcedures->sqlite->sqliteCommit();
379 : }
380 :
381 112 : state.dataErrTracking->ExitDuringSimulations = true;
382 112 : SimsDone = true;
383 112 : DisplayString(state, "Initializing New Environment Parameters");
384 :
385 112 : state.dataGlobal->BeginEnvrnFlag = true;
386 112 : state.dataGlobal->EndEnvrnFlag = false;
387 112 : state.dataEnvrn->EndMonthFlag = false;
388 112 : state.dataGlobal->WarmupFlag = true;
389 112 : state.dataGlobal->DayOfSim = 0;
390 112 : state.dataGlobal->DayOfSimChr = "0";
391 112 : state.dataReportFlag->NumOfWarmupDays = 0;
392 112 : if (state.dataEnvrn->CurrentYearIsLeapYear) {
393 0 : if (state.dataGlobal->NumOfDayInEnvrn <= 366) {
394 0 : state.dataOutputProcessor->isFinalYear = true;
395 : }
396 : } else {
397 112 : if (state.dataGlobal->NumOfDayInEnvrn <= 365) {
398 112 : state.dataOutputProcessor->isFinalYear = true;
399 : }
400 : }
401 :
402 112 : HVACManager::ResetNodeData(state); // Reset here, because some zone calcs rely on node data (e.g. ZoneITEquip)
403 :
404 : bool anyEMSRan;
405 112 : ManageEMS(state, EMSManager::EMSCallFrom::BeginNewEnvironment, anyEMSRan, ObjexxFCL::Optional_int_const()); // calling point
406 :
407 1406 : while ((state.dataGlobal->DayOfSim < state.dataGlobal->NumOfDayInEnvrn) || (state.dataGlobal->WarmupFlag)) { // Begin day loop ...
408 1295 : if (state.dataGlobal->stopSimulation) break;
409 :
410 1294 : if (state.dataSQLiteProcedures->sqlite) state.dataSQLiteProcedures->sqlite->sqliteBegin(); // setup for one transaction per day
411 :
412 1294 : ++state.dataGlobal->DayOfSim;
413 1294 : state.dataGlobal->DayOfSimChr = fmt::to_string(state.dataGlobal->DayOfSim);
414 1294 : if (!state.dataGlobal->WarmupFlag) {
415 111 : ++state.dataEnvrn->CurrentOverallSimDay;
416 111 : DisplaySimDaysProgress(state, state.dataEnvrn->CurrentOverallSimDay, state.dataEnvrn->TotalOverallSimDays);
417 : } else {
418 1183 : state.dataGlobal->DayOfSimChr = "0";
419 : }
420 1294 : state.dataGlobal->BeginDayFlag = true;
421 1294 : state.dataGlobal->EndDayFlag = false;
422 :
423 1294 : if (state.dataGlobal->WarmupFlag) {
424 1183 : ++state.dataReportFlag->NumOfWarmupDays;
425 1183 : state.dataReportFlag->cWarmupDay = fmt::to_string(state.dataReportFlag->NumOfWarmupDays);
426 1183 : DisplayString(state, "Warming up {" + state.dataReportFlag->cWarmupDay + '}');
427 111 : } else if (state.dataGlobal->DayOfSim == 1) {
428 111 : if (state.dataGlobal->KindOfSim == Constant::KindOfSim::RunPeriodWeather) {
429 0 : DisplayString(state, "Starting Simulation at " + state.dataEnvrn->CurMnDyYr + " for " + state.dataEnvrn->EnvironmentName);
430 : } else {
431 111 : DisplayString(state, "Starting Simulation at " + state.dataEnvrn->CurMnDy + " for " + state.dataEnvrn->EnvironmentName);
432 : }
433 : static constexpr std::string_view Format_700("Environment:WarmupDays,{:3}\n");
434 111 : print(state.files.eio, Format_700, state.dataReportFlag->NumOfWarmupDays);
435 0 : } else if (state.dataReportFlag->DisplayPerfSimulationFlag) {
436 0 : if (state.dataGlobal->KindOfSim == Constant::KindOfSim::RunPeriodWeather) {
437 0 : DisplayString(state, "Continuing Simulation at " + state.dataEnvrn->CurMnDyYr + " for " + state.dataEnvrn->EnvironmentName);
438 : } else {
439 0 : DisplayString(state, "Continuing Simulation at " + state.dataEnvrn->CurMnDy + " for " + state.dataEnvrn->EnvironmentName);
440 : }
441 0 : state.dataReportFlag->DisplayPerfSimulationFlag = false;
442 : }
443 : // for simulations that last longer than a week, identify when the last year of the simulation is started
444 1294 : if ((state.dataGlobal->DayOfSim > 365) && ((state.dataGlobal->NumOfDayInEnvrn - state.dataGlobal->DayOfSim) == 364) &&
445 0 : !state.dataGlobal->WarmupFlag) {
446 0 : DisplayString(state, "Starting last year of environment at: " + state.dataGlobal->DayOfSimChr);
447 0 : OutputReportTabular::ResetTabularReports(state);
448 : }
449 :
450 32327 : for (state.dataGlobal->HourOfDay = 1; state.dataGlobal->HourOfDay <= 24; ++state.dataGlobal->HourOfDay) { // Begin hour loop ...
451 31034 : if (state.dataGlobal->stopSimulation) break;
452 :
453 31033 : state.dataGlobal->BeginHourFlag = true;
454 31033 : state.dataGlobal->EndHourFlag = false;
455 :
456 196802 : for (state.dataGlobal->TimeStep = 1; state.dataGlobal->TimeStep <= state.dataGlobal->TimeStepsInHour;
457 165769 : ++state.dataGlobal->TimeStep) {
458 165770 : if (state.dataGlobal->stopSimulation) break;
459 :
460 165769 : if (state.dataGlobal->AnySlabsInModel || state.dataGlobal->AnyBasementsInModel) {
461 0 : PlantPipingSystemsManager::SimulateGroundDomains(state, false);
462 : }
463 :
464 165769 : if (AnyUnderwaterBoundaries) {
465 0 : Weather::UpdateUnderwaterBoundaries(state);
466 : }
467 :
468 331538 : if (state.dataEnvrn->varyingLocationLatSched != nullptr || state.dataEnvrn->varyingLocationLongSched != nullptr ||
469 165769 : state.dataEnvrn->varyingOrientationSched != nullptr) {
470 0 : Weather::UpdateLocationAndOrientation(state);
471 : }
472 :
473 165769 : state.dataGlobal->BeginTimeStepFlag = true;
474 165769 : ExternalInterfaceExchangeVariables(state);
475 :
476 : // Set the End__Flag variables to true if necessary. Note that
477 : // each flag builds on the previous level. EndDayFlag cannot be
478 : // .TRUE. unless EndHourFlag is also .TRUE., etc. Note that the
479 : // EndEnvrnFlag and the EndSimFlag cannot be set during warmup.
480 : // Note also that BeginTimeStepFlag, EndTimeStepFlag, and the
481 : // SubTimeStepFlags can/will be set/reset in the HVAC Manager.
482 :
483 165769 : if (state.dataGlobal->TimeStep == state.dataGlobal->TimeStepsInHour) {
484 31032 : state.dataGlobal->EndHourFlag = true;
485 31032 : if (state.dataGlobal->HourOfDay == 24) {
486 1293 : state.dataGlobal->EndDayFlag = true;
487 1293 : if ((!state.dataGlobal->WarmupFlag) && (state.dataGlobal->DayOfSim == state.dataGlobal->NumOfDayInEnvrn)) {
488 111 : state.dataGlobal->EndEnvrnFlag = true;
489 : }
490 : }
491 : }
492 :
493 165769 : Weather::ManageWeather(state);
494 :
495 165769 : ExteriorEnergyUse::ManageExteriorEnergyUse(state);
496 :
497 165769 : ManageHeatBalance(state);
498 :
499 165769 : if (oneTimeUnderwaterBoundaryCheck) {
500 65 : AnyUnderwaterBoundaries = Weather::CheckIfAnyUnderwaterBoundaries(state);
501 65 : oneTimeUnderwaterBoundaryCheck = false;
502 : }
503 :
504 165769 : state.dataGlobal->BeginHourFlag = false;
505 165769 : state.dataGlobal->BeginDayFlag = false;
506 165769 : state.dataGlobal->BeginEnvrnFlag = false;
507 165769 : state.dataGlobal->BeginSimFlag = false;
508 : } // TimeStep loop
509 :
510 31033 : state.dataGlobal->PreviousHour = state.dataGlobal->HourOfDay;
511 :
512 : } // ... End hour loop.
513 :
514 1294 : if (state.dataSQLiteProcedures->sqlite) state.dataSQLiteProcedures->sqlite->sqliteCommit(); // one transaction per day
515 :
516 : } // ... End day loop.
517 :
518 : // Need one last call to send latest states to middleware
519 112 : ExternalInterfaceExchangeVariables(state);
520 :
521 : } // ... End environment loop.
522 :
523 73 : state.dataGlobal->WarmupFlag = false;
524 :
525 73 : if (!SimsDone && state.dataGlobal->DoDesDaySim) {
526 0 : if ((state.dataEnvrn->TotDesDays + state.dataEnvrn->TotRunDesPersDays) == 0) { // if sum is 0, then there was no sizing done.
527 0 : ShowWarningError(state,
528 : "ManageSimulation: SizingPeriod:* were requested in SimulationControl but no SizingPeriod:* objects in input.");
529 : }
530 : }
531 :
532 73 : if (!SimsDone && state.dataGlobal->DoWeathSim) {
533 0 : if (!state.dataSimulationManager->RunPeriodsInInput) { // if no run period requested, and sims not done
534 0 : ShowWarningError(state, "ManageSimulation: Weather Simulation was requested in SimulationControl but no RunPeriods in input.");
535 : }
536 : }
537 :
538 73 : PlantManager::CheckOngoingPlantWarnings(state);
539 :
540 73 : if (state.dataSQLiteProcedures->sqlite) state.dataSQLiteProcedures->sqlite->sqliteBegin(); // for final data to write
541 :
542 73 : CostEstimateManager::SimCostEstimate(state);
543 :
544 73 : EconomicTariff::ComputeTariff(state); // Compute the utility bills
545 :
546 73 : EMSManager::checkForUnusedActuatorsAtEnd(state);
547 73 : EMSManager::checkSetpointNodesAtEnd(state);
548 :
549 73 : OutputProcessor::ReportForTabularReports(state); // For Energy Meters (could have other things that need to be pushed to after simulation)
550 :
551 73 : OutputReportTabular::OpenOutputTabularFile(state);
552 :
553 73 : OutputReportTabular::WriteTabularReports(state); // Create the tabular reports at completion of each
554 :
555 73 : EconomicTariff::WriteTabularTariffReports(state);
556 :
557 73 : EconomicLifeCycleCost::ComputeLifeCycleCostAndReport(state); // must be after WriteTabularReports and WriteTabularTariffReports
558 :
559 73 : OutputReportTabular::CloseOutputTabularFile(state);
560 :
561 73 : HVACControllers::DumpAirLoopStatistics(state); // Dump runtime statistics for air loop controller simulation to csv file
562 :
563 73 : CloseOutputFiles(state);
564 :
565 : // state.dataSQLiteProcedures->sqlite->createZoneExtendedOutput();
566 73 : CreateSQLiteZoneExtendedOutput(state);
567 :
568 73 : if (state.dataSQLiteProcedures->sqlite) {
569 5 : DisplayString(state, "Writing final SQL reports");
570 5 : state.dataSQLiteProcedures->sqlite->sqliteCommit(); // final transactions
571 5 : state.dataSQLiteProcedures->sqlite->initializeIndexes(); // do not create indexes (SQL) until all is done.
572 : }
573 :
574 73 : if (ErrorsFound) {
575 0 : ShowFatalError(state, "Error condition occurred. Previous Severe Errors cause termination.");
576 : }
577 73 : }
578 :
579 1172 : void GetProjectData(EnergyPlusData &state)
580 : {
581 :
582 : // SUBROUTINE INFORMATION:
583 : // AUTHOR Linda K. Lawrie
584 : // DATE WRITTEN November 1997
585 : // MODIFIED na
586 : // RE-ENGINEERED na
587 :
588 : // PURPOSE OF THIS SUBROUTINE:
589 : // This subroutine gets global project data from the input file.
590 :
591 : // METHODOLOGY EMPLOYED:
592 : // Use GetObjectItem from the Input Processor
593 :
594 : // Using/Aliasing
595 : using DataStringGlobals::MatchVersion;
596 : using namespace DataSystemVariables;
597 1172 : auto &deviationFromSetPtThresholdClg = state.dataHVACGlobal->deviationFromSetPtThresholdClg;
598 1172 : auto &deviationFromSetPtThresholdHtg = state.dataHVACGlobal->deviationFromSetPtThresholdHtg;
599 :
600 : // SUBROUTINE PARAMETER DEFINITIONS:
601 : static constexpr std::array<int, 12> Div60 = {1, 2, 3, 4, 5, 6, 10, 12, 15, 20, 30, 60};
602 :
603 : // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
604 1172 : Array1D_string Alphas(10);
605 1172 : Array1D<Real64> Number(4);
606 : int NumAlpha;
607 : int NumNumber;
608 : int IOStat;
609 : int NumDebugOut;
610 : int MinInt;
611 : int Num;
612 : int Which;
613 : bool ErrorsFound;
614 : int NumRunControl;
615 1172 : std::string VersionID;
616 1172 : std::string CurrentModuleObject;
617 : bool CondFDAlgo;
618 : int Item;
619 :
620 1172 : ErrorsFound = false;
621 :
622 1172 : CurrentModuleObject = "Version";
623 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
624 1172 : if (Num == 1) {
625 2000 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
626 : CurrentModuleObject,
627 : 1,
628 : Alphas,
629 : NumAlpha,
630 : Number,
631 : NumNumber,
632 : IOStat,
633 1000 : state.dataIPShortCut->lNumericFieldBlanks,
634 1000 : state.dataIPShortCut->lAlphaFieldBlanks,
635 1000 : state.dataIPShortCut->cAlphaFieldNames,
636 1000 : state.dataIPShortCut->cNumericFieldNames);
637 1000 : std::string::size_type const lenVer(len(MatchVersion));
638 1000 : if ((lenVer > 0) && (MatchVersion[lenVer - 1] == '0')) {
639 0 : Which = static_cast<int>(index(Alphas(1).substr(0, lenVer - 2), MatchVersion.substr(0, lenVer - 2)));
640 : } else {
641 1000 : Which = static_cast<int>(index(Alphas(1), MatchVersion));
642 : }
643 1000 : if (Which != 0) {
644 12 : ShowWarningError(state, format("{}: in IDF=\"{}\" not the same as expected=\"{}\"", CurrentModuleObject, Alphas(1), MatchVersion));
645 : }
646 1000 : VersionID = Alphas(1);
647 172 : } else if (Num == 0) {
648 172 : ShowWarningError(state, format("{}: missing in IDF, processing for EnergyPlus version=\"{}\"", CurrentModuleObject, MatchVersion));
649 : } else {
650 0 : ShowSevereError(state, format("Too many {} Objects found.", CurrentModuleObject));
651 0 : ErrorsFound = true;
652 : }
653 :
654 : // Do Mini Gets on HB Algorithm and by-surface overrides
655 1172 : CurrentModuleObject = "HeatBalanceAlgorithm";
656 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
657 1172 : CondFDAlgo = false;
658 1172 : if (Num > 0) {
659 188 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
660 : CurrentModuleObject,
661 : 1,
662 : Alphas,
663 : NumAlpha,
664 : Number,
665 : NumNumber,
666 : IOStat,
667 94 : state.dataIPShortCut->lNumericFieldBlanks,
668 94 : state.dataIPShortCut->lAlphaFieldBlanks,
669 94 : state.dataIPShortCut->cAlphaFieldNames,
670 94 : state.dataIPShortCut->cNumericFieldNames);
671 : static constexpr std::array<std::string_view, 4> condFDTypes = {
672 : "CONDUCTIONFINITEDIFFERENCE", "CONDFD", "CONDUCTIONFINITEDIFFERENCEDETAILED", "CONDUCTIONFINITEDIFFERENCESIMPLIFIED"};
673 94 : CondFDAlgo = std::find(condFDTypes.begin(), condFDTypes.end(), Alphas(1)) != condFDTypes.end();
674 : }
675 1172 : CurrentModuleObject = "SurfaceProperty:HeatTransferAlgorithm";
676 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
677 1172 : if (Num > 0) {
678 3 : for (Item = 1; Item <= Num; ++Item) {
679 4 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
680 : CurrentModuleObject,
681 : Item,
682 : Alphas,
683 : NumAlpha,
684 : Number,
685 : NumNumber,
686 : IOStat,
687 2 : state.dataIPShortCut->lNumericFieldBlanks,
688 2 : state.dataIPShortCut->lAlphaFieldBlanks,
689 2 : state.dataIPShortCut->cAlphaFieldNames,
690 2 : state.dataIPShortCut->cNumericFieldNames);
691 2 : if (Alphas(2) == "CONDUCTIONFINITEDIFFERENCE") CondFDAlgo = true;
692 : }
693 : }
694 1172 : CurrentModuleObject = "SurfaceProperty:HeatTransferAlgorithm:MultipleSurface";
695 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
696 1172 : if (Num > 0) {
697 0 : for (Item = 1; Item <= Num; ++Item) {
698 0 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
699 : CurrentModuleObject,
700 : 1,
701 : Alphas,
702 : NumAlpha,
703 : Number,
704 : NumNumber,
705 : IOStat,
706 0 : state.dataIPShortCut->lNumericFieldBlanks,
707 0 : state.dataIPShortCut->lAlphaFieldBlanks,
708 0 : state.dataIPShortCut->cAlphaFieldNames,
709 0 : state.dataIPShortCut->cNumericFieldNames);
710 0 : if (Alphas(3) == "CONDUCTIONFINITEDIFFERENCE") CondFDAlgo = true;
711 : }
712 : }
713 1172 : CurrentModuleObject = "SurfaceProperty:HeatTransferAlgorithm:SurfaceList";
714 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
715 1172 : if (Num > 0) {
716 0 : for (Item = 1; Item <= Num; ++Item) {
717 0 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
718 : CurrentModuleObject,
719 : 1,
720 0 : state.dataIPShortCut->cAlphaArgs,
721 : NumAlpha,
722 : Number,
723 : NumNumber,
724 : IOStat,
725 0 : state.dataIPShortCut->lNumericFieldBlanks,
726 0 : state.dataIPShortCut->lAlphaFieldBlanks,
727 0 : state.dataIPShortCut->cAlphaFieldNames,
728 0 : state.dataIPShortCut->cNumericFieldNames);
729 0 : if (state.dataIPShortCut->cAlphaArgs(2) == "CONDUCTIONFINITEDIFFERENCE") CondFDAlgo = true;
730 : }
731 : }
732 1172 : CurrentModuleObject = "SurfaceProperty:HeatTransferAlgorithm:Construction";
733 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
734 1172 : if (Num > 0) {
735 2 : for (Item = 1; Item <= Num; ++Item) {
736 2 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
737 : CurrentModuleObject,
738 : 1,
739 1 : state.dataIPShortCut->cAlphaArgs,
740 : NumAlpha,
741 : Number,
742 : NumNumber,
743 : IOStat,
744 1 : state.dataIPShortCut->lNumericFieldBlanks,
745 1 : state.dataIPShortCut->lAlphaFieldBlanks,
746 1 : state.dataIPShortCut->cAlphaFieldNames,
747 1 : state.dataIPShortCut->cNumericFieldNames);
748 1 : if (state.dataIPShortCut->cAlphaArgs(2) == "CONDUCTIONFINITEDIFFERENCE") CondFDAlgo = true;
749 : }
750 : }
751 :
752 1172 : CurrentModuleObject = "Timestep";
753 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
754 1172 : if (Num == 1) {
755 2002 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
756 : CurrentModuleObject,
757 : 1,
758 : Alphas,
759 : NumAlpha,
760 : Number,
761 : NumNumber,
762 : IOStat,
763 1001 : state.dataIPShortCut->lNumericFieldBlanks,
764 1001 : state.dataIPShortCut->lAlphaFieldBlanks,
765 1001 : state.dataIPShortCut->cAlphaFieldNames,
766 1001 : state.dataIPShortCut->cNumericFieldNames);
767 1001 : state.dataGlobal->TimeStepsInHour = Number(1);
768 1001 : if (state.dataSysVars->ciForceTimeStep) {
769 0 : state.dataGlobal->TimeStepsInHour = 2; // Force 30 minute time steps on CI
770 : }
771 1001 : if (state.dataGlobal->TimeStepsInHour <= 0 || state.dataGlobal->TimeStepsInHour > 60) {
772 0 : Alphas(1) = fmt::to_string(state.dataGlobal->TimeStepsInHour);
773 0 : ShowWarningError(state, format("{}: Requested number ({}) invalid, Defaulted to 4", CurrentModuleObject, Alphas(1)));
774 0 : state.dataGlobal->TimeStepsInHour = 4;
775 1001 : } else if (mod(60, state.dataGlobal->TimeStepsInHour) != 0) {
776 0 : MinInt = 9999;
777 0 : for (Num = 1; Num <= 12; ++Num) {
778 0 : if (std::abs(state.dataGlobal->TimeStepsInHour - Div60[Num - 1]) > MinInt) continue;
779 0 : MinInt = state.dataGlobal->TimeStepsInHour - Div60[Num - 1];
780 0 : Which = Num;
781 : }
782 0 : ShowWarningError(state,
783 0 : format("{}: Requested number ({}) not evenly divisible into 60, defaulted to nearest ({}).",
784 : CurrentModuleObject,
785 0 : state.dataGlobal->TimeStepsInHour,
786 0 : Div60[Which - 1]));
787 0 : state.dataGlobal->TimeStepsInHour = Div60[Which - 1];
788 : }
789 1001 : if (CondFDAlgo && state.dataGlobal->TimeStepsInHour < 20) {
790 0 : ShowWarningError(state,
791 0 : format("{}: Requested number ({}) cannot be used when Conduction Finite Difference algorithm is selected.",
792 : CurrentModuleObject,
793 0 : state.dataGlobal->TimeStepsInHour));
794 0 : ShowContinueError(state, format("...{} is set to 20.", CurrentModuleObject));
795 0 : state.dataGlobal->TimeStepsInHour = 20;
796 : }
797 1001 : if (state.dataGlobal->TimeStepsInHour < 4 && state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Zone") > 0) {
798 14 : ShowWarningError(state,
799 14 : format("{}: Requested number ({}) is less than the suggested minimum of 4.",
800 : CurrentModuleObject,
801 7 : state.dataGlobal->TimeStepsInHour));
802 14 : ShowContinueError(state,
803 14 : format("Please see entry for {} in Input/Output Reference for discussion of considerations.", CurrentModuleObject));
804 : }
805 171 : } else if (Num == 0 && state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Zone") > 0 && !CondFDAlgo) {
806 4 : ShowWarningError(state, format("No {} object found. Number of TimeSteps in Hour defaulted to 4.", CurrentModuleObject));
807 4 : state.dataGlobal->TimeStepsInHour = 4;
808 167 : } else if (Num == 0 && !CondFDAlgo) {
809 167 : state.dataGlobal->TimeStepsInHour = 4;
810 0 : } else if (Num == 0 && state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Zone") > 0 && CondFDAlgo) {
811 0 : ShowWarningError(state, format("No {} object found. Number of TimeSteps in Hour defaulted to 20.", CurrentModuleObject));
812 0 : ShowContinueError(state, "...Due to presence of Conduction Finite Difference Algorithm selection.");
813 0 : state.dataGlobal->TimeStepsInHour = 20;
814 0 : } else if (Num == 0 && CondFDAlgo) {
815 0 : state.dataGlobal->TimeStepsInHour = 20;
816 : } else {
817 0 : ShowSevereError(state, format("Too many {} Objects found.", CurrentModuleObject));
818 0 : ErrorsFound = true;
819 : }
820 :
821 1172 : state.dataGlobal->TimeStepZone = 1.0 / double(state.dataGlobal->TimeStepsInHour);
822 1172 : state.dataGlobal->MinutesInTimeStep = state.dataGlobal->TimeStepZone * 60;
823 1172 : state.dataGlobal->TimeStepZoneSec = state.dataGlobal->TimeStepZone * Constant::rSecsInHour;
824 :
825 1172 : CurrentModuleObject = "ConvergenceLimits";
826 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
827 1172 : if (Num == 1) {
828 22 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
829 : CurrentModuleObject,
830 : 1,
831 : Alphas,
832 : NumAlpha,
833 : Number,
834 : NumNumber,
835 : IOStat,
836 11 : state.dataIPShortCut->lNumericFieldBlanks,
837 11 : state.dataIPShortCut->lAlphaFieldBlanks,
838 11 : state.dataIPShortCut->cAlphaFieldNames,
839 11 : state.dataIPShortCut->cNumericFieldNames);
840 11 : MinInt = int(Number(1));
841 11 : if (MinInt > state.dataGlobal->MinutesInTimeStep) {
842 0 : MinInt = state.dataGlobal->MinutesInTimeStep;
843 : }
844 11 : if (MinInt < 0 || MinInt > 60) {
845 0 : ShowWarningError(
846 : state,
847 0 : format(
848 0 : "{}: Requested {} ({}) invalid. Set to 1 minute.", CurrentModuleObject, state.dataIPShortCut->cNumericFieldNames(1), MinInt));
849 0 : state.dataConvergeParams->MinTimeStepSys = 1.0 / 60.0;
850 11 : } else if (MinInt == 0) { // Set to TimeStepZone
851 0 : state.dataConvergeParams->MinTimeStepSys = state.dataGlobal->TimeStepZone;
852 : } else {
853 11 : state.dataConvergeParams->MinTimeStepSys = double(MinInt) / 60.0;
854 : }
855 11 : state.dataConvergeParams->MaxIter = int(Number(2));
856 11 : if (state.dataConvergeParams->MaxIter <= 0) {
857 0 : state.dataConvergeParams->MaxIter = 20;
858 : }
859 11 : if (!state.dataIPShortCut->lNumericFieldBlanks(3)) state.dataConvergeParams->MinPlantSubIterations = int(Number(3));
860 11 : if (!state.dataIPShortCut->lNumericFieldBlanks(4)) state.dataConvergeParams->MaxPlantSubIterations = int(Number(4));
861 : // trap bad values
862 11 : if (state.dataConvergeParams->MinPlantSubIterations < 1) state.dataConvergeParams->MinPlantSubIterations = 1;
863 11 : if (state.dataConvergeParams->MaxPlantSubIterations < 3) state.dataConvergeParams->MaxPlantSubIterations = 3;
864 11 : if (state.dataConvergeParams->MinPlantSubIterations > state.dataConvergeParams->MaxPlantSubIterations)
865 0 : state.dataConvergeParams->MaxPlantSubIterations = state.dataConvergeParams->MinPlantSubIterations + 1;
866 :
867 1161 : } else if (Num == 0) {
868 1161 : state.dataConvergeParams->MinTimeStepSys = 1.0 / 60.0;
869 1161 : state.dataConvergeParams->MaxIter = 20;
870 1161 : state.dataConvergeParams->MinPlantSubIterations = 2;
871 1161 : state.dataConvergeParams->MaxPlantSubIterations = 8;
872 : } else {
873 0 : ShowSevereError(state, format("Too many {} Objects found.", CurrentModuleObject));
874 0 : ErrorsFound = true;
875 : }
876 :
877 1172 : state.dataHVACGlobal->LimitNumSysSteps = int(state.dataGlobal->TimeStepZone / state.dataConvergeParams->MinTimeStepSys);
878 :
879 1172 : state.dataReportFlag->DebugOutput = false;
880 1172 : state.dataReportFlag->EvenDuringWarmup = false;
881 1172 : CurrentModuleObject = "Output:DebuggingData";
882 1172 : NumDebugOut = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
883 1172 : if (NumDebugOut > 1) {
884 1 : ShowWarningError(state, format("{}: More than 1 occurrence of this object found, only first will be used.", CurrentModuleObject));
885 : }
886 1172 : if (NumDebugOut > 0) {
887 3 : state.dataInputProcessing->inputProcessor->getObjectItem(state, CurrentModuleObject, 1, Alphas, NumAlpha, Number, NumNumber, IOStat);
888 3 : if (NumAlpha >= 1) {
889 3 : state.dataReportFlag->DebugOutput = Util::SameString(Alphas(1), "Yes");
890 : }
891 3 : if (NumAlpha >= 2) {
892 3 : state.dataReportFlag->EvenDuringWarmup = Util::SameString(Alphas(2), "Yes");
893 : }
894 : }
895 :
896 : {
897 1172 : CurrentModuleObject = "Output:Diagnostics";
898 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
899 1172 : if (Num > 1) {
900 : // Let it slide, but warn
901 : // ErrorsFound = true;
902 1 : ShowWarningError(state, format("{}: More than 1 occurrence of this object found, only first will be used.", CurrentModuleObject));
903 : }
904 1172 : auto const instances = state.dataInputProcessing->inputProcessor->epJSON.find(CurrentModuleObject);
905 :
906 1172 : if (instances != state.dataInputProcessing->inputProcessor->epJSON.end()) {
907 21 : auto &instancesValue = instances.value();
908 21 : for (auto instance = instancesValue.begin(); instance != instancesValue.end(); ++instance) {
909 21 : auto const &fields = instance.value();
910 21 : std::string const &thisObjectName = instance.key();
911 21 : state.dataInputProcessing->inputProcessor->markObjectAsUsed(CurrentModuleObject, thisObjectName);
912 :
913 21 : auto diagnosticsExtensibles = fields.find("diagnostics");
914 21 : if (diagnosticsExtensibles != fields.end()) {
915 58 : for (auto &diagnosticsExtensible : diagnosticsExtensibles.value()) {
916 :
917 : // We want to avoid cryptic failures such as this one: "[json.exception.out_of_range.403] key 'key' not found"
918 : // Which happens if you put an "empty" entry in the extensible portion
919 38 : auto it = diagnosticsExtensible.find("key");
920 38 : if (it == diagnosticsExtensible.end()) {
921 2 : ShowWarningError(state,
922 2 : format("{}: empty key found, consider removing it to avoid this warning.", CurrentModuleObject));
923 1 : continue;
924 : }
925 37 : std::string diagnosticName = it->get<std::string>();
926 :
927 37 : if (Util::SameString(diagnosticName, "DisplayExtraWarnings")) {
928 16 : state.dataGlobal->DisplayExtraWarnings = true;
929 21 : } else if (Util::SameString(diagnosticName, "DisplayAdvancedReportVariables")) {
930 4 : state.dataGlobal->DisplayAdvancedReportVariables = true;
931 17 : } else if (Util::SameString(diagnosticName, "DisplayAllWarnings")) {
932 2 : state.dataGlobal->DisplayAllWarnings = true;
933 2 : state.dataGlobal->DisplayExtraWarnings = true;
934 2 : state.dataGlobal->DisplayUnusedObjects = true;
935 2 : state.dataGlobal->DisplayUnusedSchedules = true;
936 15 : } else if (Util::SameString(diagnosticName, "DisplayUnusedObjects")) {
937 1 : state.dataGlobal->DisplayUnusedObjects = true;
938 14 : } else if (Util::SameString(diagnosticName, "DisplayUnusedSchedules")) {
939 2 : state.dataGlobal->DisplayUnusedSchedules = true;
940 12 : } else if (Util::SameString(diagnosticName, "DisplayZoneAirHeatBalanceOffBalance")) {
941 1 : state.dataGlobal->DisplayZoneAirHeatBalanceOffBalance = true;
942 11 : } else if (Util::SameString(diagnosticName, "DoNotMirrorDetachedShading")) {
943 1 : state.dataReportFlag->MakeMirroredDetachedShading = false;
944 10 : } else if (Util::SameString(diagnosticName, "DoNotMirrorAttachedShading")) {
945 1 : state.dataReportFlag->MakeMirroredAttachedShading = false;
946 9 : } else if (Util::SameString(diagnosticName, "ReportDuringWarmup")) {
947 1 : state.dataSysVars->ReportDuringWarmup = true;
948 8 : } else if (Util::SameString(diagnosticName, "DisplayWeatherMissingDataWarnings")) {
949 1 : state.dataEnvrn->DisplayWeatherMissingDataWarnings = true;
950 7 : } else if (Util::SameString(diagnosticName, "IgnoreSolarRadiation")) { // TODO: Not a valid key choice
951 1 : state.dataEnvrn->IgnoreSolarRadiation = true;
952 6 : } else if (Util::SameString(diagnosticName, "IgnoreBeamRadiation")) { // TODO: Not a valid key choice
953 1 : state.dataEnvrn->IgnoreBeamRadiation = true;
954 5 : } else if (Util::SameString(diagnosticName, "IgnoreDiffuseRadiation")) { // TODO: Not a valid key choice
955 1 : state.dataEnvrn->IgnoreDiffuseRadiation = true;
956 4 : } else if (Util::SameString(diagnosticName, "DeveloperFlag")) { // TODO: Not a valid key choice
957 1 : state.dataSysVars->DeveloperFlag = true;
958 3 : } else if (Util::SameString(diagnosticName, "TimingFlag")) { // TODO: Not a valid key choice
959 1 : state.dataSysVars->TimingFlag = true;
960 2 : } else if (Util::SameString(diagnosticName, "ReportDetailedWarmupConvergence")) {
961 1 : state.dataSysVars->ReportDetailedWarmupConvergence = true;
962 1 : } else if (Util::SameString(diagnosticName, "ReportDuringHVACSizingSimulation")) {
963 1 : state.dataSysVars->ReportDuringHVACSizingSimulation = true;
964 0 : } else if (Util::SameString(diagnosticName, "CreateMinimalSurfaceVariables")) { // TODO: Not a valid key choice
965 0 : continue;
966 : // CreateMinimalSurfaceVariables=.TRUE.
967 0 : } else if (Util::SameString(diagnosticName, "CreateNormalSurfaceVariables")) { // TODO: Not a valid key choice
968 0 : continue;
969 : // IF (CreateMinimalSurfaceVariables) THEN
970 : // CALL ShowWarningError(state, 'GetProjectData: '//TRIM(CurrentModuleObject)//'=''// &
971 : // TRIM(diagnosticName)//'', prior set=true for this condition reverts to false.')
972 : // ENDIF
973 : // CreateMinimalSurfaceVariables=.FALSE.
974 0 : } else if (!diagnosticName.empty()) {
975 0 : ShowWarningError(state,
976 0 : format("GetProjectData: {}=\"{}\", Invalid value for field, entered value ignored.",
977 : CurrentModuleObject,
978 : diagnosticName));
979 : }
980 37 : }
981 : }
982 :
983 : // Don't process the duplicate ones
984 21 : break;
985 : }
986 : }
987 : }
988 :
989 1172 : CurrentModuleObject = "OutputControl:ReportingTolerances";
990 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
991 1172 : if (Num > 0) {
992 0 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
993 : CurrentModuleObject,
994 : 1,
995 : Alphas,
996 : NumAlpha,
997 : Number,
998 : NumNumber,
999 : IOStat,
1000 0 : state.dataIPShortCut->lNumericFieldBlanks,
1001 0 : state.dataIPShortCut->lAlphaFieldBlanks,
1002 0 : state.dataIPShortCut->cAlphaFieldNames,
1003 0 : state.dataIPShortCut->cNumericFieldNames);
1004 0 : if (!state.dataIPShortCut->lNumericFieldBlanks(1)) {
1005 0 : deviationFromSetPtThresholdHtg = -Number(1);
1006 : } else {
1007 0 : deviationFromSetPtThresholdHtg = -0.2;
1008 : }
1009 0 : if (!state.dataIPShortCut->lNumericFieldBlanks(2)) {
1010 0 : deviationFromSetPtThresholdClg = Number(2);
1011 : } else {
1012 0 : deviationFromSetPtThresholdClg = 0.2;
1013 : }
1014 : }
1015 :
1016 1172 : state.dataHeatBalMgr->CurrentModuleObject = "OutputControl:ResilienceSummaries";
1017 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, state.dataHeatBalMgr->CurrentModuleObject);
1018 1172 : if (Num > 0) {
1019 0 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
1020 0 : state.dataHeatBalMgr->CurrentModuleObject,
1021 : 1,
1022 : Alphas,
1023 : NumAlpha,
1024 : Number,
1025 : NumNumber,
1026 : IOStat,
1027 0 : state.dataIPShortCut->lNumericFieldBlanks,
1028 0 : state.dataIPShortCut->lAlphaFieldBlanks,
1029 0 : state.dataIPShortCut->cAlphaFieldNames,
1030 0 : state.dataIPShortCut->cNumericFieldNames);
1031 0 : if (NumAlpha > 0) {
1032 0 : state.dataHeatBal->heatIndexMethod =
1033 0 : static_cast<DataHeatBalance::HeatIndexMethod>(getEnumValue(DataHeatBalance::HeatIndexMethodUC, Util::makeUPPER(Alphas(1))));
1034 : }
1035 : }
1036 :
1037 1172 : state.dataGlobal->DoZoneSizing = false;
1038 1172 : state.dataGlobal->DoSystemSizing = false;
1039 1172 : state.dataGlobal->DoPlantSizing = false;
1040 1172 : state.dataGlobal->DoDesDaySim = true;
1041 1172 : state.dataGlobal->DoWeathSim = true;
1042 1172 : state.dataGlobal->DoHVACSizingSimulation = false;
1043 1172 : state.dataGlobal->HVACSizingSimMaxIterations = 0;
1044 1172 : CurrentModuleObject = "SimulationControl";
1045 1172 : NumRunControl = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
1046 1172 : if (NumRunControl > 0) {
1047 162 : state.dataSimulationManager->RunControlInInput = true;
1048 324 : state.dataInputProcessing->inputProcessor->getObjectItem(state,
1049 : CurrentModuleObject,
1050 : 1,
1051 : Alphas,
1052 : NumAlpha,
1053 : Number,
1054 : NumNumber,
1055 : IOStat,
1056 162 : state.dataIPShortCut->lNumericFieldBlanks,
1057 162 : state.dataIPShortCut->lAlphaFieldBlanks,
1058 162 : state.dataIPShortCut->cAlphaFieldNames,
1059 162 : state.dataIPShortCut->cNumericFieldNames);
1060 162 : if (Alphas(1) == "YES") state.dataGlobal->DoZoneSizing = true;
1061 162 : if (Alphas(2) == "YES") state.dataGlobal->DoSystemSizing = true;
1062 162 : if (Alphas(3) == "YES") state.dataGlobal->DoPlantSizing = true;
1063 162 : if (Alphas(4) == "NO") state.dataGlobal->DoDesDaySim = false;
1064 162 : if (Alphas(5) == "NO") state.dataGlobal->DoWeathSim = false;
1065 162 : if (NumAlpha > 5) {
1066 162 : if (Alphas(6) == "YES") state.dataGlobal->DoHVACSizingSimulation = true;
1067 : }
1068 : }
1069 1172 : if (state.dataSysVars->DDOnly) {
1070 26 : state.dataGlobal->DoDesDaySim = true;
1071 26 : state.dataGlobal->DoWeathSim = false;
1072 : }
1073 1172 : if (state.dataSysVars->FullAnnualRun) {
1074 0 : state.dataGlobal->DoDesDaySim = false;
1075 0 : state.dataGlobal->DoWeathSim = true;
1076 : }
1077 :
1078 1184 : if ((!state.dataGlobal->DoDesDaySim && !state.dataGlobal->DoWeathSim && !state.dataGlobal->DoHVACSizingSimulation) &&
1079 12 : (state.dataGlobal->DoZoneSizing || state.dataGlobal->DoSystemSizing)) {
1080 11 : state.dataGlobal->DoPureLoadCalc = true;
1081 : }
1082 :
1083 1172 : CurrentModuleObject = "PerformancePrecisionTradeoffs";
1084 1172 : auto const instances = state.dataInputProcessing->inputProcessor->epJSON.find(CurrentModuleObject);
1085 1172 : Num = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, CurrentModuleObject);
1086 1172 : if (Num > 1) {
1087 0 : ErrorsFound = true;
1088 0 : ShowFatalError(state, format("GetProjectData: Only one (\"1\") {} object per simulation is allowed.", CurrentModuleObject));
1089 : }
1090 1172 : state.dataGlobal->createPerfLog = Num > 0;
1091 1172 : std::string overrideModeValue = "Normal";
1092 1172 : if (instances != state.dataInputProcessing->inputProcessor->epJSON.end()) {
1093 4 : auto &instancesValue = instances.value();
1094 8 : for (auto instance = instancesValue.begin(); instance != instancesValue.end(); ++instance) {
1095 4 : auto const &fields = instance.value();
1096 4 : std::string const &thisObjectName = instance.key();
1097 4 : state.dataInputProcessing->inputProcessor->markObjectAsUsed(CurrentModuleObject, thisObjectName);
1098 12 : if (fields.find("use_coil_direct_solutions") != fields.end()) {
1099 4 : state.dataGlobal->DoCoilDirectSolutions = Util::makeUPPER(fields.at("use_coil_direct_solutions").get<std::string>()) == "YES";
1100 : }
1101 12 : if (fields.find("zone_radiant_exchange_algorithm") != fields.end()) {
1102 0 : state.dataHeatBalIntRadExchg->CarrollMethod =
1103 0 : Util::makeUPPER(fields.at("zone_radiant_exchange_algorithm").get<std::string>()) == "CARROLLMRT";
1104 : }
1105 12 : if (fields.find("use_representative_surfaces_for_calculations") != fields.end()) {
1106 0 : state.dataSurface->UseRepresentativeSurfaceCalculations =
1107 0 : Util::makeUPPER(fields.at("use_representative_surfaces_for_calculations").get<std::string>()) == "YES";
1108 : }
1109 4 : bool overrideTimestep(false);
1110 4 : bool overrideZoneAirHeatBalAlg(false);
1111 4 : bool overrideMinNumWarmupDays(false);
1112 4 : bool overrideBeginEnvResetSuppress(false);
1113 4 : bool overrideMaxZoneTempDiff(false);
1114 4 : bool overrideSystemTimestep(false);
1115 4 : bool overrideMaxAllowedDelTemp(false);
1116 4 : bool overridePsychTsatFnPb(false);
1117 4 : state.dataZoneTempPredictorCorrector->OscillationVariablesNeeded = true;
1118 12 : if (fields.find("override_mode") != fields.end()) {
1119 2 : overrideModeValue = Util::makeUPPER(fields.at("override_mode").get<std::string>());
1120 2 : if (overrideModeValue == "NORMAL") {
1121 : // no overrides
1122 2 : } else if (overrideModeValue == "MODE01") {
1123 : // Zone Time step (TimeStep object) will be set to one timestep per hour
1124 2 : overrideTimestep = true;
1125 0 : } else if (overrideModeValue == "MODE02") {
1126 : // Mode01 plus ZoneAirHeatBalanceAlgorithm will be set to Euler
1127 0 : overrideTimestep = true;
1128 0 : overrideZoneAirHeatBalAlg = true;
1129 0 : } else if (overrideModeValue == "MODE03") {
1130 : // Mode02 plus Minimum Number of Warmup Days will be set to 1
1131 0 : overrideTimestep = true;
1132 0 : overrideZoneAirHeatBalAlg = true;
1133 0 : overrideMinNumWarmupDays = true;
1134 0 : } else if (overrideModeValue == "MODE04") {
1135 : // Mode03 plus Begin Environment Reset Mode will be set to SuppressAllBeginEnvironmentResets
1136 0 : overrideTimestep = true;
1137 0 : overrideZoneAirHeatBalAlg = true;
1138 0 : overrideMinNumWarmupDays = true;
1139 0 : overrideBeginEnvResetSuppress = true;
1140 0 : } else if (overrideModeValue == "MODE05") {
1141 : // Mode04 plus Minimun System Timestep will be set to 1hr
1142 0 : overrideTimestep = true;
1143 0 : overrideZoneAirHeatBalAlg = true;
1144 0 : overrideMinNumWarmupDays = true;
1145 0 : overrideBeginEnvResetSuppress = true;
1146 0 : overrideSystemTimestep = true;
1147 0 : } else if (overrideModeValue == "MODE06") {
1148 : // Mode05 plus cubic spline interpolations in replacement of the original psychrometric function PsychTsatFnPb
1149 0 : overrideTimestep = true;
1150 0 : overrideZoneAirHeatBalAlg = true;
1151 0 : overrideMinNumWarmupDays = true;
1152 0 : overrideBeginEnvResetSuppress = true;
1153 0 : overrideSystemTimestep = true;
1154 0 : overridePsychTsatFnPb = true;
1155 0 : } else if (overrideModeValue == "MODE07") {
1156 : // Mode06 plus internal variable MaxZoneTempDiff will be set to 1.00
1157 0 : overrideTimestep = true;
1158 0 : overrideZoneAirHeatBalAlg = true;
1159 0 : overrideMinNumWarmupDays = true;
1160 0 : overrideBeginEnvResetSuppress = true;
1161 0 : overrideSystemTimestep = true;
1162 0 : overrideMaxZoneTempDiff = true;
1163 0 : overridePsychTsatFnPb = true;
1164 0 : } else if (overrideModeValue == "MODE08") {
1165 : // Mode07 plus internal variable MaxAllowedDelTemp will be set to 0.1
1166 0 : overrideTimestep = true;
1167 0 : overrideZoneAirHeatBalAlg = true;
1168 0 : overrideMinNumWarmupDays = true;
1169 0 : overrideBeginEnvResetSuppress = true;
1170 0 : overrideSystemTimestep = true;
1171 0 : overrideMaxZoneTempDiff = true;
1172 0 : overrideMaxAllowedDelTemp = true;
1173 0 : overridePsychTsatFnPb = true;
1174 0 : } else if (overrideModeValue == "ADVANCED") {
1175 0 : bool advancedModeUsed = false;
1176 0 : if (fields.find("maxzonetempdiff") != fields.end()) { // not required field, has default value
1177 0 : state.dataConvergeParams->MaxZoneTempDiff = fields.at("maxzonetempdiff").get<Real64>();
1178 0 : ShowWarningError(state,
1179 0 : format("PerformancePrecisionTradeoffs using the Advanced Override Mode, MaxZoneTempDiff set to: {:.4R}",
1180 0 : state.dataConvergeParams->MaxZoneTempDiff));
1181 0 : advancedModeUsed = true;
1182 : }
1183 0 : if (fields.find("maxalloweddeltemp") != fields.end()) { // not required field, has default value
1184 0 : state.dataHeatBal->MaxAllowedDelTemp = fields.at("maxalloweddeltemp").get<Real64>();
1185 0 : ShowWarningError(
1186 : state,
1187 0 : format("PerformancePrecisionTradeoffs using the Advanced Override Mode, MaxAllowedDelTemp set to: {:.4R}",
1188 0 : state.dataHeatBal->MaxAllowedDelTemp));
1189 0 : advancedModeUsed = true;
1190 : }
1191 0 : if (advancedModeUsed) {
1192 0 : ShowContinueError(state,
1193 : "...Care should be used when using the Advanced Override Mode. Results may be significantly different "
1194 : "than a simulation not using this mode.");
1195 : } else {
1196 0 : ShowWarningError(
1197 : state, "PerformancePrecisionTradeoffs using the Advanced Override Mode but no specific parameters have been set.");
1198 : }
1199 : } else {
1200 0 : ShowSevereError(state,
1201 0 : format("Invalid over ride mode specified in PerformancePrecisionTradeoffs object: {}", overrideModeValue));
1202 : }
1203 :
1204 2 : if (overrideTimestep) {
1205 4 : ShowWarningError(state, "Due to PerformancePrecisionTradeoffs Override Mode, the Number of TimeSteps has been changed to 1.");
1206 2 : state.dataGlobal->TimeStepsInHour = 1;
1207 2 : state.dataGlobal->TimeStepZone = 1.0 / double(state.dataGlobal->TimeStepsInHour);
1208 2 : state.dataGlobal->MinutesInTimeStep = state.dataGlobal->TimeStepZone * Constant::rMinutesInHour;
1209 2 : state.dataGlobal->TimeStepZoneSec = state.dataGlobal->TimeStepZone * Constant::rSecsInHour;
1210 2 : state.dataGlobal->OverrideTimestep = true;
1211 : }
1212 2 : if (overrideZoneAirHeatBalAlg) {
1213 0 : ShowWarningError(
1214 : state,
1215 : "Due to PerformancePrecisionTradeoffs Override Mode, the ZoneAirHeatBalanceAlgorithm has been changed to EulerMethod.");
1216 0 : state.dataHeatBal->OverrideZoneAirSolutionAlgo = true;
1217 : }
1218 2 : if (overrideMinNumWarmupDays) {
1219 0 : ShowWarningError(
1220 : state, "Due to PerformancePrecisionTradeoffs Override Mode, the Minimum Number of Warmup Days has been changed to 1.");
1221 0 : state.dataHeatBal->MinNumberOfWarmupDays = 1;
1222 : }
1223 2 : if (overrideBeginEnvResetSuppress) {
1224 0 : ShowWarningError(state,
1225 : "Due to PerformancePrecisionTradeoffs Override Mode, the Begin Environment Reset Mode has been changed to "
1226 : "SuppressAllBeginEnvironmentResets.");
1227 0 : state.dataEnvrn->forceBeginEnvResetSuppress = true;
1228 : }
1229 2 : if (overrideSystemTimestep) {
1230 0 : ShowWarningError(
1231 : state, "Due to PerformancePrecisionTradeoffs Override Mode, the minimum System TimeSteps has been changed to 1 hr.");
1232 0 : int MinTimeStepSysOverrideValue = 60.0;
1233 0 : if (MinTimeStepSysOverrideValue > state.dataGlobal->MinutesInTimeStep) {
1234 0 : MinTimeStepSysOverrideValue = state.dataGlobal->MinutesInTimeStep;
1235 : }
1236 0 : state.dataConvergeParams->MinTimeStepSys = MinTimeStepSysOverrideValue / 60.0;
1237 0 : state.dataHVACGlobal->LimitNumSysSteps = int(state.dataGlobal->TimeStepZone / state.dataConvergeParams->MinTimeStepSys);
1238 : }
1239 2 : if (overridePsychTsatFnPb) {
1240 0 : ShowWarningError(state,
1241 : "Due to PerformancePrecisionTradeoffs Override Mode, the saturated temperature will be calculated using "
1242 : "cubic spline interpolations in replacement of PsychTsatFnPb .");
1243 : // Mode06 CSpline interpolation (64 Pa bin size + 20/16 bit)
1244 0 : state.dataPsychrometrics->useInterpolationPsychTsatFnPb = true;
1245 : #ifdef EP_cache_PsyTsatFnPb
1246 0 : state.dataPsychCache->tsatprecision_bits = 20;
1247 : #endif
1248 : }
1249 2 : if (overrideMaxZoneTempDiff) {
1250 0 : ShowWarningError(
1251 : state, "Due to PerformancePrecisionTradeoffs Override Mode, internal variable MaxZoneTempDiff will be set to 1.0 .");
1252 0 : state.dataConvergeParams->MaxZoneTempDiff = 1.0;
1253 : }
1254 2 : if (overrideMaxAllowedDelTemp) {
1255 0 : ShowWarningError(
1256 : state, "Due to PerformancePrecisionTradeoffs Override Mode, internal variable MaxAllowedDelTemp will be set to 0.1 .");
1257 0 : state.dataHeatBal->MaxAllowedDelTemp = 0.1;
1258 : }
1259 : }
1260 : }
1261 : }
1262 1172 : if (ErrorsFound) {
1263 0 : ShowFatalError(state, "Errors found getting Project Input");
1264 : }
1265 :
1266 1172 : print(state.files.eio, "{}\n", "! <Version>, Version ID");
1267 : static constexpr std::string_view Format_721(" Version, {}\n");
1268 1172 : print(state.files.eio, Format_721, VersionID);
1269 :
1270 1172 : print(state.files.eio, "{}\n", "! <Timesteps per Hour>, #TimeSteps, Minutes per TimeStep {minutes}");
1271 : static constexpr std::string_view Format_731(" Timesteps per Hour, {:2}, {:2}\n");
1272 1172 : print(state.files.eio, Format_731, state.dataGlobal->TimeStepsInHour, state.dataGlobal->MinutesInTimeStep);
1273 :
1274 1172 : print(state.files.eio,
1275 : "{}\n",
1276 : "! <System Convergence Limits>, Minimum System TimeStep {minutes}, Max HVAC Iterations, Minimum Plant "
1277 : "Iterations, Maximum Plant Iterations");
1278 1172 : MinInt = state.dataConvergeParams->MinTimeStepSys * 60.0;
1279 : static constexpr std::string_view Format_733(" System Convergence Limits, {}, {}, {}, {}\n");
1280 1172 : print(state.files.eio,
1281 : Format_733,
1282 : MinInt,
1283 1172 : state.dataConvergeParams->MaxIter,
1284 1172 : state.dataConvergeParams->MinPlantSubIterations,
1285 1172 : state.dataConvergeParams->MaxPlantSubIterations);
1286 :
1287 1172 : if (state.dataGlobal->DoZoneSizing) {
1288 72 : Alphas(1) = "Yes";
1289 : } else {
1290 1100 : Alphas(1) = "No";
1291 : }
1292 1172 : if (state.dataGlobal->DoSystemSizing) {
1293 50 : Alphas(2) = "Yes";
1294 : } else {
1295 1122 : Alphas(2) = "No";
1296 : }
1297 1172 : if (state.dataGlobal->DoPlantSizing) {
1298 16 : Alphas(3) = "Yes";
1299 : } else {
1300 1156 : Alphas(3) = "No";
1301 : }
1302 1172 : if (state.dataGlobal->DoDesDaySim) {
1303 1142 : Alphas(4) = "Yes";
1304 : } else {
1305 30 : Alphas(4) = "No";
1306 : }
1307 1172 : if (state.dataGlobal->DoWeathSim) {
1308 1035 : Alphas(5) = "Yes";
1309 : } else {
1310 137 : Alphas(5) = "No";
1311 : }
1312 1172 : if (state.dataGlobal->DoHVACSizingSimulation) {
1313 1 : Alphas(6) = "Yes";
1314 1 : if (NumNumber >= 1) {
1315 1 : state.dataGlobal->HVACSizingSimMaxIterations = Number(1);
1316 : }
1317 : } else {
1318 1171 : Alphas(6) = "No";
1319 : }
1320 :
1321 1172 : print(state.files.eio,
1322 : "{}\n",
1323 : "! <Simulation Control>, Do Zone Sizing, Do System Sizing, Do Plant Sizing, Do Design Days, Do Weather "
1324 : "Simulation, Do HVAC Sizing Simulation");
1325 1172 : print(state.files.eio, " Simulation Control");
1326 8204 : for (Num = 1; Num <= 6; ++Num) {
1327 7032 : print(state.files.eio, ", {}", Alphas(Num));
1328 : }
1329 1172 : print(state.files.eio, "\n");
1330 :
1331 : // Performance Precision Tradeoffs
1332 1172 : if (state.dataGlobal->DoCoilDirectSolutions) {
1333 1 : Alphas(1) = "Yes";
1334 3 : ShowWarningError(state, "PerformancePrecisionTradeoffs: Coil Direct Solution simulation is selected.");
1335 : } else {
1336 1171 : Alphas(1) = "No";
1337 : }
1338 1172 : if (state.dataHeatBalIntRadExchg->CarrollMethod) {
1339 0 : Alphas(2) = "CarrollMRT";
1340 0 : ShowWarningError(state, "PerformancePrecisionTradeoffs: Carroll MRT radiant exchange method is selected.");
1341 : } else {
1342 1172 : Alphas(2) = "ScriptF";
1343 : }
1344 1172 : Alphas(3) = overrideModeValue;
1345 1172 : Alphas(4) = fmt::to_string(state.dataGlobal->TimeStepsInHour);
1346 1172 : if (state.dataHeatBal->OverrideZoneAirSolutionAlgo) {
1347 0 : Alphas(5) = "Yes";
1348 : } else {
1349 1172 : Alphas(5) = "No";
1350 : }
1351 1172 : Alphas(6) = fmt::to_string(state.dataHeatBal->MinNumberOfWarmupDays);
1352 1172 : if (state.dataEnvrn->forceBeginEnvResetSuppress) {
1353 0 : Alphas(7) = "Yes";
1354 : } else {
1355 1172 : Alphas(7) = "No";
1356 : }
1357 1172 : Alphas(8) = format("{:.1R}", state.dataConvergeParams->MinTimeStepSys * 60.0);
1358 1172 : Alphas(9) = format("{:.3R}", state.dataConvergeParams->MaxZoneTempDiff);
1359 1172 : Alphas(10) = format("{:.4R}", state.dataHeatBal->MaxAllowedDelTemp);
1360 : std::string pptHeader = "! <Performance Precision Tradeoffs>, Use Coil Direct Simulation, "
1361 : "Zone Radiant Exchange Algorithm, Override Mode, Number of Timestep In Hour, "
1362 : "Force Euler Method, Minimum Number of Warmup Days, Force Suppress All Begin Environment Resets, "
1363 1172 : "Minimum System Timestep, MaxZoneTempDiff, MaxAllowedDelTemp";
1364 1172 : print(state.files.eio, "{}\n", pptHeader);
1365 1172 : print(state.files.eio, " Performance Precision Tradeoffs");
1366 12892 : for (Num = 1; Num <= 10; ++Num) {
1367 11720 : print(state.files.eio, ", {}", Alphas(Num));
1368 : }
1369 1172 : print(state.files.eio, "\n");
1370 :
1371 1172 : print(state.files.eio,
1372 : "{}\n",
1373 : "! <Output Reporting Tolerances>, Tolerance for Time Heating Setpoint Not Met, Tolerance for Zone Cooling Setpoint Not Met Time");
1374 : // Formats
1375 : static constexpr std::string_view Format_751(" Output Reporting Tolerances, {:.3R}, {:.3R}, \n");
1376 :
1377 1172 : print(state.files.eio, Format_751, std::abs(deviationFromSetPtThresholdHtg), deviationFromSetPtThresholdClg);
1378 :
1379 : // IF (DisplayExtraWarnings) THEN
1380 : // Write(OutputFileInits,740)
1381 : // Write(OutputFileInits,741) (TRIM(Alphas(Num)),Num=1,5)
1382 : // 742 Format('! <Display Extra Warnings>, Display Advanced Report Variables, Do Not Mirror Detached Shading')
1383 : // IF (DisplayAdvancedReportVariables) THEN
1384 : // NumOut1='Yes'
1385 : // ELSE
1386 : // NumOut2='No'
1387 : // ENDIF
1388 : // IF (.not. MakeMirroredDetachedShading) THEN
1389 : // NumOut1='Yes'
1390 : // ELSE
1391 : // NumOut2='No'
1392 : // ENDIF
1393 : // unused0909743 Format(' Display Extra Warnings',2(', ',A))
1394 : // ENDIF
1395 1172 : if (state.dataGlobal->createPerfLog) {
1396 4 : writeInitialPerfLogValues(state, overrideModeValue);
1397 : }
1398 1172 : }
1399 :
1400 5 : void writeInitialPerfLogValues(EnergyPlusData &state, std::string const ¤tOverrideModeValue)
1401 : // write the input related portions of the .perflog
1402 : // J.Glazer February 2020
1403 : {
1404 5 : Util::appendPerfLog(state,
1405 : "Program, Version, TimeStamp",
1406 5 : state.dataStrGlobals->VerStringVar); // this string already includes three portions and has commas
1407 15 : Util::appendPerfLog(state, "Use Coil Direct Solution", bool_to_string(state.dataGlobal->DoCoilDirectSolutions));
1408 5 : if (state.dataHeatBalIntRadExchg->CarrollMethod) {
1409 0 : Util::appendPerfLog(state, "Zone Radiant Exchange Algorithm", "CarrollMRT");
1410 : } else {
1411 20 : Util::appendPerfLog(state, "Zone Radiant Exchange Algorithm", "ScriptF");
1412 : }
1413 5 : Util::appendPerfLog(state, "Override Mode", currentOverrideModeValue);
1414 15 : Util::appendPerfLog(state, "Number of Timesteps per Hour", fmt::to_string(state.dataGlobal->TimeStepsInHour));
1415 15 : Util::appendPerfLog(state, "Minimum Number of Warmup Days", fmt::to_string(state.dataHeatBal->MinNumberOfWarmupDays));
1416 15 : Util::appendPerfLog(state, "SuppressAllBeginEnvironmentResets", bool_to_string(state.dataEnvrn->forceBeginEnvResetSuppress));
1417 15 : Util::appendPerfLog(state, "Minimum System Timestep", format("{:.1R}", state.dataConvergeParams->MinTimeStepSys * 60.0));
1418 15 : Util::appendPerfLog(state, "MaxZoneTempDiff", format("{:.2R}", state.dataConvergeParams->MaxZoneTempDiff));
1419 15 : Util::appendPerfLog(state, "MaxAllowedDelTemp", format("{:.4R}", state.dataHeatBal->MaxAllowedDelTemp));
1420 5 : }
1421 :
1422 12 : std::string bool_to_string(bool logical)
1423 : {
1424 12 : if (logical) {
1425 4 : return ("True");
1426 : } else {
1427 20 : return ("False");
1428 : }
1429 : }
1430 :
1431 77 : void CheckForMisMatchedEnvironmentSpecifications(EnergyPlusData &state)
1432 : {
1433 :
1434 : // SUBROUTINE INFORMATION:
1435 : // AUTHOR Linda Lawrie
1436 : // DATE WRITTEN August 2008
1437 : // MODIFIED na
1438 : // RE-ENGINEERED na
1439 :
1440 : // PURPOSE OF THIS SUBROUTINE:
1441 : // In response to CR 7518, this routine will check to see if a proper combination of SimulationControl, RunPeriod,
1442 : // SizingPeriod:*, etc are entered to proceed with a simulation.
1443 :
1444 : // METHODOLOGY EMPLOYED:
1445 : // For now (8/2008), the routine will query several objects in the input. And try to produce warnings or
1446 : // fatals as a result.
1447 :
1448 : // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
1449 : int NumZoneSizing;
1450 : int NumSystemSizing;
1451 : int NumPlantSizing;
1452 : int NumDesignDays;
1453 : int NumRunPeriodDesign;
1454 : int NumSizingDays;
1455 : bool WeatherFileAttached;
1456 : bool ErrorsFound;
1457 :
1458 77 : ErrorsFound = false;
1459 77 : NumZoneSizing = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Sizing:Zone");
1460 77 : NumSystemSizing = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Sizing:System");
1461 77 : NumPlantSizing = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Sizing:Plant");
1462 77 : NumDesignDays = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "SizingPeriod:DesignDay");
1463 77 : NumRunPeriodDesign = state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "SizingPeriod:WeatherFileDays") +
1464 77 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "SizingPeriod:WeatherFileConditionType");
1465 77 : NumSizingDays = NumDesignDays + NumRunPeriodDesign;
1466 :
1467 77 : WeatherFileAttached = FileSystem::fileExists(state.files.inputWeatherFilePath.filePath);
1468 :
1469 77 : if (state.dataSimulationManager->RunControlInInput) {
1470 76 : if (state.dataGlobal->DoZoneSizing) {
1471 34 : if (NumZoneSizing > 0 && NumSizingDays == 0) {
1472 0 : ErrorsFound = true;
1473 0 : ShowSevereError(
1474 : state, "CheckEnvironmentSpecifications: Sizing for Zones has been requested but there are no design environments specified.");
1475 0 : ShowContinueError(state, "...Add appropriate SizingPeriod:* objects for your simulation.");
1476 : }
1477 34 : if (NumZoneSizing > 0 && NumRunPeriodDesign > 0 && !WeatherFileAttached) {
1478 0 : ErrorsFound = true;
1479 0 : ShowSevereError(state,
1480 : "CheckEnvironmentSpecifications: Sizing for Zones has been requested; Design period from the weather file "
1481 : "requested; but no weather file specified.");
1482 : }
1483 : }
1484 76 : if (state.dataGlobal->DoSystemSizing) {
1485 23 : if (NumSystemSizing > 0 && NumSizingDays == 0) {
1486 0 : ErrorsFound = true;
1487 0 : ShowSevereError(
1488 : state,
1489 : "CheckEnvironmentSpecifications: Sizing for Systems has been requested but there are no design environments specified.");
1490 0 : ShowContinueError(state, "...Add appropriate SizingPeriod:* objects for your simulation.");
1491 : }
1492 23 : if (NumSystemSizing > 0 && NumRunPeriodDesign > 0 && !WeatherFileAttached) {
1493 0 : ErrorsFound = true;
1494 0 : ShowSevereError(state,
1495 : "CheckEnvironmentSpecifications: Sizing for Systems has been requested; Design period from the weather file "
1496 : "requested; but no weather file specified.");
1497 : }
1498 : }
1499 76 : if (state.dataGlobal->DoPlantSizing) {
1500 5 : if (NumPlantSizing > 0 && NumSizingDays == 0) {
1501 0 : ErrorsFound = true;
1502 0 : ShowSevereError(state,
1503 : "CheckEnvironmentSpecifications: Sizing for Equipment/Plants has been requested but there are no design "
1504 : "environments specified.");
1505 0 : ShowContinueError(state, "...Add appropriate SizingPeriod:* objects for your simulation.");
1506 : }
1507 5 : if (NumPlantSizing > 0 && NumRunPeriodDesign > 0 && !WeatherFileAttached) {
1508 0 : ErrorsFound = true;
1509 0 : ShowSevereError(state,
1510 : "CheckEnvironmentSpecifications: Sizing for Equipment/Plants has been requested; Design period from the weather "
1511 : "file requested; but no weather file specified.");
1512 : }
1513 : }
1514 76 : if (state.dataGlobal->DoDesDaySim && NumSizingDays == 0) {
1515 0 : ShowWarningError(state,
1516 : "CheckEnvironmentSpecifications: SimulationControl specified doing design day simulations, but no design "
1517 : "environments specified.");
1518 0 : ShowContinueError(
1519 : state,
1520 : "...No design environment results produced. For these results, add appropriate SizingPeriod:* objects for your simulation.");
1521 : }
1522 76 : if (state.dataGlobal->DoDesDaySim && NumRunPeriodDesign > 0 && !WeatherFileAttached) {
1523 0 : ErrorsFound = true;
1524 0 : ShowSevereError(state,
1525 : "CheckEnvironmentSpecifications: SimulationControl specified doing design day simulations; weather file design "
1526 : "environments specified; but no weather file specified.");
1527 : }
1528 76 : if (state.dataGlobal->DoWeathSim && !state.dataSimulationManager->RunPeriodsInInput) {
1529 0 : ShowWarningError(state,
1530 : "CheckEnvironmentSpecifications: SimulationControl specified doing weather simulations, but no run periods for "
1531 : "weather file specified. No annual results produced.");
1532 : }
1533 76 : if (state.dataGlobal->DoWeathSim && state.dataSimulationManager->RunPeriodsInInput && !WeatherFileAttached) {
1534 0 : ShowWarningError(state,
1535 : "CheckEnvironmentSpecifications: SimulationControl specified doing weather simulations; run periods for weather "
1536 : "file specified; but no weather file specified.");
1537 : }
1538 : }
1539 :
1540 77 : if (!state.dataGlobal->DoDesDaySim && !state.dataGlobal->DoWeathSim) {
1541 : // This amounts to checking: (!DoHVACSizingSimulation && !DoZoneSizing && !DoSystemSizing)
1542 10 : if (!state.dataGlobal->DoHVACSizingSimulation && !state.dataGlobal->DoPureLoadCalc) {
1543 2 : ShowSevereError(state, "All elements of SimulationControl are set to \"No\". No simulations can be done. Program terminates.");
1544 1 : ErrorsFound = true;
1545 : } else {
1546 27 : ShowWarningError(state,
1547 : "\"Run Simulation for Sizing Periods\" and \"Run Simulation for Weather File Run Periods\" are both set to \"No\". "
1548 : "No simulations will be performed, and most input will not be read.");
1549 : }
1550 : }
1551 :
1552 77 : if (ErrorsFound) {
1553 3 : ShowFatalError(state, "Program terminates due to preceding conditions.");
1554 : }
1555 76 : }
1556 :
1557 75 : void CheckForRequestedReporting(EnergyPlusData &state)
1558 : {
1559 :
1560 : // SUBROUTINE INFORMATION:
1561 : // AUTHOR Linda Lawrie
1562 : // DATE WRITTEN January 2009
1563 :
1564 : // PURPOSE OF THIS SUBROUTINE:
1565 : // EnergyPlus does not automatically produce any results files. Because of this, users may not request
1566 : // reports and may get confused when nothing is produced. This routine will provide a warning when
1567 : // results should be produced (either sizing periods or weather files are run) but no reports are
1568 : // requested.
1569 :
1570 75 : bool SimPeriods = (state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "SizingPeriod:DesignDay") > 0 ||
1571 1 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "SizingPeriod:WeatherFileDays") > 0 ||
1572 77 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "SizingPeriod:WeatherFileConditionType") > 0 ||
1573 1 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "RunPeriod") > 0);
1574 :
1575 75 : if ((state.dataGlobal->DoDesDaySim || state.dataGlobal->DoWeathSim || state.dataGlobal->DoPureLoadCalc) && SimPeriods) {
1576 : bool ReportingRequested =
1577 74 : (state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Output:Table:SummaryReports") > 0 ||
1578 35 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Output:Table:TimeBins") > 0 ||
1579 35 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Output:Table:Monthly") > 0 ||
1580 35 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Output:Table:Annual") > 0 ||
1581 35 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Output:Variable") > 0 ||
1582 34 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Output:Meter") > 0 ||
1583 33 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Output:Meter:MeterFileOnly") > 0 ||
1584 142 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Output:Meter:Cumulative") > 0 ||
1585 33 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "Output:Meter:Cumulative:MeterFileOnly") > 0);
1586 : // Not testing for : Output:SQLite or Output:EnvironmentalImpactFactors
1587 74 : if (!ReportingRequested) {
1588 66 : ShowWarningError(state, "No reporting elements have been requested. No simulation results produced.");
1589 99 : ShowContinueError(state,
1590 : "...Review requirements such as \"Output:Table:SummaryReports\", \"Output:Table:Monthly\", \"Output:Variable\", "
1591 : "\"Output:Meter\" and others.");
1592 : }
1593 : }
1594 75 : }
1595 :
1596 0 : std::unique_ptr<std::ostream> OpenStreamFile(EnergyPlusData &state, const fs::path &filePath, std::ios_base::openmode mode)
1597 : {
1598 0 : auto result = std::make_unique<std::ofstream>(filePath, mode); // (AUTO_OK_UPTR)
1599 0 : if (!result->good()) {
1600 0 : ShowFatalError(state, format("OpenOutputFiles: Could not open file {} for output (write).", filePath));
1601 : }
1602 0 : return result;
1603 0 : }
1604 :
1605 0 : std::unique_ptr<fmt::ostream> OpenFmtStreamFile(EnergyPlusData &state, const fs::path &filePath)
1606 : {
1607 0 : std::unique_ptr<fmt::ostream> result = nullptr;
1608 : #ifdef _WIN32
1609 : std::string filePathStr = FileSystem::toString(filePath);
1610 : const char *path = filePathStr.c_str();
1611 : #else
1612 0 : const char *path = filePath.c_str();
1613 : #endif
1614 : try {
1615 0 : auto f = fmt::output_file(path, fmt::buffer_size = (2 << 17)); // (AUTO_OK_OBJ)
1616 0 : result = std::make_unique<fmt::ostream>(std::move(f));
1617 0 : } catch (const std::system_error &error) {
1618 0 : ShowSevereError(state, error.what());
1619 0 : ShowFatalError(state, format("OpenOutputFiles: Could not open file {} for output (write).", filePath));
1620 0 : }
1621 0 : return result;
1622 0 : }
1623 :
1624 1154 : void OpenOutputFiles(EnergyPlusData &state)
1625 : {
1626 :
1627 : // SUBROUTINE INFORMATION:
1628 : // AUTHOR Rick Strand
1629 : // DATE WRITTEN June 1997
1630 : // MODIFIED na
1631 : // RE-ENGINEERED na
1632 :
1633 : // PURPOSE OF THIS SUBROUTINE:
1634 : // This subroutine opens all of the input and output files needed for
1635 : // an EnergyPlus run.
1636 :
1637 1154 : state.dataGlobal->StdOutputRecordCount = 0;
1638 2308 : state.files.eso.ensure_open(state, "OpenOutputFiles", state.files.outputControl.eso);
1639 1154 : print(state.files.eso, "Program Version,{}\n", state.dataStrGlobals->VerStringVar);
1640 :
1641 : // Open the Initialization Output File
1642 2308 : state.files.eio.ensure_open(state, "OpenOutputFiles", state.files.outputControl.eio);
1643 1154 : print(state.files.eio, "Program Version,{}\n", state.dataStrGlobals->VerStringVar);
1644 :
1645 : // Open the Meters Output File
1646 2308 : state.files.mtr.ensure_open(state, "OpenOutputFiles", state.files.outputControl.mtr);
1647 1154 : print(state.files.mtr, "Program Version,{}\n", state.dataStrGlobals->VerStringVar);
1648 :
1649 : // Open the Branch-Node Details Output File
1650 2308 : state.files.bnd.ensure_open(state, "OpenOutputFiles", state.files.outputControl.bnd);
1651 1154 : print(state.files.bnd, "Program Version,{}\n", state.dataStrGlobals->VerStringVar);
1652 1154 : }
1653 :
1654 74 : void CloseOutputFiles(EnergyPlusData &state)
1655 : {
1656 :
1657 : // SUBROUTINE INFORMATION:
1658 : // AUTHOR Rick Strand
1659 : // DATE WRITTEN June 1997
1660 : // MODIFIED na
1661 : // RE-ENGINEERED na
1662 :
1663 : // PURPOSE OF THIS SUBROUTINE:
1664 : // This subroutine closes all of the input and output files needed for
1665 : // an EnergyPlus run. It also prints the end of data marker for each
1666 : // output file.
1667 :
1668 : // METHODOLOGY EMPLOYED:
1669 : // na
1670 :
1671 : // REFERENCES:
1672 : // na
1673 :
1674 : // Using/Aliasing
1675 : using namespace DataOutputs;
1676 : using namespace DataRuntimeLanguage;
1677 : using namespace DataSystemVariables;
1678 :
1679 : // SUBROUTINE PARAMETER DEFINITIONS:
1680 : static constexpr std::string_view EndOfDataString("End of Data"); // Signifies the end of the data block in the output file
1681 :
1682 : // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
1683 74 : std::string cEnvSetThreads;
1684 74 : std::string cepEnvSetThreads;
1685 74 : std::string cIDFSetThreads;
1686 :
1687 148 : state.files.audit.ensure_open(state, "CloseOutputFiles", state.files.outputControl.audit);
1688 : constexpr static std::string_view variable_fmt = " {}={:12}\n";
1689 : // Record some items on the audit file
1690 74 : print(state.files.audit, variable_fmt, "NumOfRVariable", state.dataOutputProcessor->NumOfRVariable_Setup);
1691 74 : print(state.files.audit, variable_fmt, "NumOfRVariable(Total)", state.dataOutputProcessor->NumTotalRVariable);
1692 74 : print(state.files.audit, variable_fmt, "NumOfRVariable(Actual)", state.dataOutputProcessor->NumOfRVariable);
1693 74 : print(state.files.audit, variable_fmt, "NumOfRVariable(Summed)", state.dataOutputProcessor->NumOfRVariable_Sum);
1694 74 : print(state.files.audit, variable_fmt, "NumOfRVariable(Meter)", state.dataOutputProcessor->NumOfRVariable_Meter);
1695 74 : print(state.files.audit, variable_fmt, "NumOfIVariable", state.dataOutputProcessor->NumOfIVariable_Setup);
1696 74 : print(state.files.audit, variable_fmt, "NumOfIVariable(Total)", state.dataOutputProcessor->NumTotalIVariable);
1697 74 : print(state.files.audit, variable_fmt, "NumOfIVariable(Actual)", state.dataOutputProcessor->NumOfIVariable);
1698 74 : print(state.files.audit, variable_fmt, "NumOfIVariable(Summed)", state.dataOutputProcessor->NumOfIVariable_Sum);
1699 : // print(state.files.audit, variable_fmt, "MaxRVariable", state.dataOutputProcessor->MaxRVariable);
1700 : // print(state.files.audit, variable_fmt, "MaxIVariable", state.dataOutputProcessor->MaxIVariable);
1701 74 : print(state.files.audit, variable_fmt, "NumEnergyMeters", state.dataOutputProcessor->meters.size());
1702 : // print(state.files.audit, variable_fmt, "NumVarMeterArrays", state.dataOutputProcessor->NumVarMeterArrays);
1703 74 : print(state.files.audit, variable_fmt, "maxUniqueKeyCount", state.dataOutRptTab->maxUniqueKeyCount);
1704 74 : print(state.files.audit, variable_fmt, "maxNumberOfFigures", state.dataSolarShading->maxNumberOfFigures);
1705 74 : print(state.files.audit, variable_fmt, "MAXHCArrayBounds", state.dataSolarShading->MAXHCArrayBounds);
1706 74 : print(state.files.audit, variable_fmt, "MaxVerticesPerSurface", state.dataSurface->MaxVerticesPerSurface);
1707 : // print(state.files.audit, variable_fmt, "NumReportList", state.dataOutputProcessor->NumReportList);
1708 : // print(state.files.audit, variable_fmt, "InstMeterCacheSize", state.dataOutputProcessor->InstMeterCacheSize);
1709 74 : if (state.dataSysVars->SutherlandHodgman) {
1710 74 : if (state.dataSysVars->SlaterBarsky) {
1711 0 : print(state.files.audit, " {}\n", "ClippingAlgorithm=SlaterBarskyandSutherlandHodgman");
1712 : } else {
1713 74 : print(state.files.audit, " {}\n", "ClippingAlgorithm=SutherlandHodgman");
1714 : }
1715 : } else {
1716 0 : print(state.files.audit, "{}\n", "ClippingAlgorithm=ConvexWeilerAtherton");
1717 : }
1718 74 : print(state.files.audit, variable_fmt, "MonthlyFieldSetInputCount", state.dataOutRptTab->MonthlyFieldSetInputCount);
1719 74 : print(state.files.audit, variable_fmt, "NumConsideredOutputVariables", state.dataOutput->NumConsideredOutputVariables);
1720 74 : print(state.files.audit, variable_fmt, "MaxConsideredOutputVariables", state.dataOutput->MaxConsideredOutputVariables);
1721 :
1722 74 : print(state.files.audit, variable_fmt, "numActuatorsUsed", state.dataRuntimeLang->numActuatorsUsed);
1723 74 : print(state.files.audit, variable_fmt, "numEMSActuatorsAvailable", state.dataRuntimeLang->numEMSActuatorsAvailable);
1724 74 : print(state.files.audit, variable_fmt, "maxEMSActuatorsAvailable", state.dataRuntimeLang->maxEMSActuatorsAvailable);
1725 74 : print(state.files.audit, variable_fmt, "numInternalVariablesUsed", state.dataRuntimeLang->NumInternalVariablesUsed);
1726 74 : print(state.files.audit, variable_fmt, "numEMSInternalVarsAvailable", state.dataRuntimeLang->numEMSInternalVarsAvailable);
1727 74 : print(state.files.audit, variable_fmt, "maxEMSInternalVarsAvailable", state.dataRuntimeLang->maxEMSInternalVarsAvailable);
1728 :
1729 74 : print(state.files.audit, variable_fmt, "NumOfNodeConnections", state.dataBranchNodeConnections->NumOfNodeConnections);
1730 74 : print(state.files.audit, variable_fmt, "MaxNumOfNodeConnections", state.dataBranchNodeConnections->MaxNumOfNodeConnections);
1731 : #ifdef EP_Count_Calls
1732 : print(state.files.audit, variable_fmt, "NumShadow_Calls", state.dataTimingsData->NumShadow_Calls);
1733 : print(state.files.audit, variable_fmt, "NumShadowAtTS_Calls", state.dataTimingsData->NumShadowAtTS_Calls);
1734 : print(state.files.audit, variable_fmt, "NumClipPoly_Calls", state.dataTimingsData->NumClipPoly_Calls);
1735 : print(state.files.audit, variable_fmt, "NumInitSolar_Calls", state.dataTimingsData->NumInitSolar_Calls);
1736 : print(state.files.audit, variable_fmt, "NumAnisoSky_Calls", state.dataTimingsData->NumAnisoSky_Calls);
1737 : print(state.files.audit, variable_fmt, "NumDetPolyOverlap_Calls", state.dataTimingsData->NumDetPolyOverlap_Calls);
1738 : print(state.files.audit, variable_fmt, "NumCalcPerSolBeam_Calls", state.dataTimingsData->NumCalcPerSolBeam_Calls);
1739 : print(state.files.audit, variable_fmt, "NumDetShadowCombs_Calls", state.dataTimingsData->NumDetShadowCombs_Calls);
1740 : print(state.files.audit, variable_fmt, "NumIntSolarDist_Calls", state.dataTimingsData->NumIntSolarDist_Calls);
1741 : print(state.files.audit, variable_fmt, "NumIntRadExchange_Calls", state.dataTimingsData->NumIntRadExchange_Calls);
1742 : print(state.files.audit, variable_fmt, "NumIntRadExchangeZ_Calls", state.dataTimingsData->NumIntRadExchangeZ_Calls);
1743 : print(state.files.audit, variable_fmt, "NumIntRadExchangeMain_Calls", state.dataTimingsData->NumIntRadExchangeMain_Calls);
1744 : print(state.files.audit, variable_fmt, "NumIntRadExchangeOSurf_Calls", state.dataTimingsData->NumIntRadExchangeOSurf_Calls);
1745 : print(state.files.audit, variable_fmt, "NumIntRadExchangeISurf_Calls", state.dataTimingsData->NumIntRadExchangeISurf_Calls);
1746 : print(state.files.audit, variable_fmt, "NumMaxInsideSurfIterations", state.dataTimingsData->NumMaxInsideSurfIterations);
1747 : print(state.files.audit, variable_fmt, "NumCalcScriptF_Calls", state.dataTimingsData->NumCalcScriptF_Calls);
1748 : #endif
1749 :
1750 74 : print(state.files.eso, "{}\n", EndOfDataString);
1751 74 : if (state.dataGlobal->StdOutputRecordCount > 0) {
1752 25 : print(state.files.eso, variable_fmt, "Number of Records Written", state.dataGlobal->StdOutputRecordCount);
1753 25 : state.files.eso.close();
1754 : } else {
1755 49 : state.files.eso.del();
1756 : }
1757 :
1758 74 : if (state.dataHeatBal->AnyCondFD) { // echo out relaxation factor, it may have been changed by the program
1759 2 : print(
1760 2 : state.files.eio, "{}\n", "! <ConductionFiniteDifference Numerical Parameters>, Starting Relaxation Factor, Final Relaxation Factor");
1761 2 : print(state.files.eio,
1762 : "ConductionFiniteDifference Numerical Parameters, {:.3R}, {:.3R}\n",
1763 2 : state.dataHeatBal->CondFDRelaxFactorInput,
1764 2 : state.dataHeatBal->CondFDRelaxFactor);
1765 : }
1766 : // Report number of threads to eio file
1767 : static constexpr std::string_view ThreadingHeader(
1768 : "! <Program Control Information:Threads/Parallel Sims>, Threading Supported,Maximum Number of "
1769 : "Threads, Env Set Threads (OMP_NUM_THREADS), EP Env Set Threads (EP_OMP_NUM_THREADS), IDF Set "
1770 : "Threads, Number of Threads Used (Interior Radiant Exchange), Number Nominal Surfaces, Number "
1771 : "Parallel Sims");
1772 74 : print(state.files.eio, "{}\n", ThreadingHeader);
1773 : static constexpr std::string_view ThreadReport("Program Control:Threads/Parallel Sims, {},{}, {}, {}, {}, {}, {}, {}\n");
1774 74 : if (state.dataSysVars->Threading) {
1775 0 : if (state.dataSysVars->iEnvSetThreads == 0) {
1776 0 : cEnvSetThreads = "Not Set";
1777 : } else {
1778 0 : cEnvSetThreads = fmt::to_string(state.dataSysVars->iEnvSetThreads);
1779 : }
1780 0 : if (state.dataSysVars->iepEnvSetThreads == 0) {
1781 0 : cepEnvSetThreads = "Not Set";
1782 : } else {
1783 0 : cepEnvSetThreads = fmt::to_string(state.dataSysVars->iepEnvSetThreads);
1784 : }
1785 0 : if (state.dataSysVars->iIDFSetThreads == 0) {
1786 0 : cIDFSetThreads = "Not Set";
1787 : } else {
1788 0 : cIDFSetThreads = fmt::to_string(state.dataSysVars->iIDFSetThreads);
1789 : }
1790 0 : if (state.dataSysVars->lnumActiveSims) {
1791 0 : print(state.files.eio,
1792 : ThreadReport,
1793 : "Yes",
1794 0 : state.dataSysVars->MaxNumberOfThreads,
1795 : cEnvSetThreads,
1796 : cepEnvSetThreads,
1797 : cIDFSetThreads,
1798 0 : state.dataSysVars->NumberIntRadThreads,
1799 0 : state.dataSysVars->iNominalTotSurfaces,
1800 0 : state.dataSysVars->inumActiveSims);
1801 : } else {
1802 0 : print(state.files.eio,
1803 : ThreadReport,
1804 : "Yes",
1805 0 : state.dataSysVars->MaxNumberOfThreads,
1806 : cEnvSetThreads,
1807 : cepEnvSetThreads,
1808 : cIDFSetThreads,
1809 0 : state.dataSysVars->NumberIntRadThreads,
1810 0 : state.dataSysVars->iNominalTotSurfaces,
1811 : "N/A");
1812 : }
1813 : } else { // no threading
1814 74 : if (state.dataSysVars->lnumActiveSims) {
1815 0 : print(state.files.eio,
1816 : ThreadReport,
1817 : "No",
1818 0 : state.dataSysVars->MaxNumberOfThreads,
1819 : "N/A",
1820 : "N/A",
1821 : "N/A",
1822 : "N/A",
1823 : "N/A",
1824 0 : state.dataSysVars->inumActiveSims);
1825 : } else {
1826 74 : print(state.files.eio, ThreadReport, "No", state.dataSysVars->MaxNumberOfThreads, "N/A", "N/A", "N/A", "N/A", "N/A", "N/A");
1827 : }
1828 : }
1829 :
1830 : // Close the Initialization Output File
1831 74 : print(state.files.eio, "{}\n", EndOfDataString);
1832 74 : state.files.eio.close();
1833 :
1834 : // Close the Meters Output File
1835 74 : print(state.files.mtr, "{}\n", EndOfDataString);
1836 74 : print(state.files.mtr, " Number of Records Written={:12}\n", state.dataGlobal->StdMeterRecordCount);
1837 74 : if (state.dataGlobal->StdMeterRecordCount > 0) {
1838 22 : state.files.mtr.close();
1839 : } else {
1840 52 : state.files.mtr.del();
1841 : }
1842 :
1843 : // Close the External Shading Output File
1844 74 : state.files.shade.close();
1845 74 : }
1846 :
1847 91 : void SetupSimulation(EnergyPlusData &state, bool &ErrorsFound)
1848 : {
1849 :
1850 : // SUBROUTINE INFORMATION:
1851 : // AUTHOR B. Griffith/L. Lawrie
1852 : // DATE WRITTEN May 2008
1853 : // MODIFIED na
1854 : // RE-ENGINEERED na
1855 :
1856 : // PURPOSE OF THIS SUBROUTINE:
1857 : // execute a few time steps of a simulation to facilitate setting up model
1858 : // developed to resolve reverse DD problems caused be the differences
1859 : // that stem from setup and information gathering that occurs during the first pass.
1860 :
1861 : // METHODOLOGY EMPLOYED:
1862 : // Using global flag (kickoff simulation), only a few time steps are executed.
1863 : // global flag is used in other parts of simulation to terminate quickly.
1864 :
1865 : // Using/Aliasing
1866 : using CostEstimateManager::SimCostEstimate;
1867 : using ExteriorEnergyUse::ManageExteriorEnergyUse;
1868 :
1869 91 : bool Available = true;
1870 :
1871 264 : while (Available) { // do for each environment
1872 :
1873 264 : Weather::GetNextEnvironment(state, Available, ErrorsFound);
1874 :
1875 263 : if (!Available) break;
1876 174 : if (ErrorsFound) break;
1877 :
1878 174 : state.dataGlobal->BeginEnvrnFlag = true;
1879 174 : state.dataGlobal->EndEnvrnFlag = false;
1880 174 : state.dataEnvrn->EndMonthFlag = false;
1881 174 : state.dataGlobal->WarmupFlag = true;
1882 174 : state.dataGlobal->DayOfSim = 0;
1883 :
1884 174 : ++state.dataGlobal->DayOfSim;
1885 174 : state.dataGlobal->BeginDayFlag = true;
1886 174 : state.dataGlobal->EndDayFlag = false;
1887 :
1888 174 : state.dataGlobal->HourOfDay = 1;
1889 :
1890 174 : state.dataGlobal->BeginHourFlag = true;
1891 174 : state.dataGlobal->EndHourFlag = false;
1892 :
1893 174 : state.dataGlobal->TimeStep = 1;
1894 :
1895 174 : if (state.dataSysVars->DeveloperFlag) DisplayString(state, "Initializing Simulation - timestep 1:" + state.dataEnvrn->EnvironmentName);
1896 :
1897 174 : state.dataGlobal->BeginTimeStepFlag = true;
1898 :
1899 174 : Weather::ManageWeather(state);
1900 :
1901 174 : ManageExteriorEnergyUse(state);
1902 :
1903 174 : ManageHeatBalance(state);
1904 :
1905 173 : state.dataGlobal->BeginHourFlag = false;
1906 173 : state.dataGlobal->BeginDayFlag = false;
1907 173 : state.dataGlobal->BeginEnvrnFlag = false;
1908 173 : state.dataGlobal->BeginSimFlag = false;
1909 :
1910 : // ! do another timestep=1
1911 173 : if (state.dataSysVars->DeveloperFlag)
1912 0 : DisplayString(state, "Initializing Simulation - 2nd timestep 1:" + state.dataEnvrn->EnvironmentName);
1913 :
1914 173 : Weather::ManageWeather(state);
1915 :
1916 173 : ManageExteriorEnergyUse(state);
1917 :
1918 173 : ManageHeatBalance(state);
1919 :
1920 : // do an end of day, end of environment time step
1921 :
1922 173 : state.dataGlobal->HourOfDay = 24;
1923 173 : state.dataGlobal->TimeStep = state.dataGlobal->TimeStepsInHour;
1924 173 : state.dataGlobal->EndEnvrnFlag = true;
1925 :
1926 173 : if (state.dataSysVars->DeveloperFlag)
1927 0 : DisplayString(state, "Initializing Simulation - hour 24 timestep 1:" + state.dataEnvrn->EnvironmentName);
1928 173 : Weather::ManageWeather(state);
1929 :
1930 173 : ManageExteriorEnergyUse(state);
1931 :
1932 173 : ManageHeatBalance(state);
1933 :
1934 : } // ... End environment loop.
1935 :
1936 89 : if (state.dataGlobal->AnySlabsInModel || state.dataGlobal->AnyBasementsInModel) {
1937 0 : PlantPipingSystemsManager::SimulateGroundDomains(state, true);
1938 : }
1939 :
1940 89 : if (!ErrorsFound) SimCostEstimate(state); // basically will get and check input
1941 89 : if (ErrorsFound) ShowFatalError(state, "Previous conditions cause program termination.");
1942 89 : }
1943 :
1944 73 : void ReportNodeConnections(EnergyPlusData &state)
1945 : {
1946 :
1947 : // SUBROUTINE INFORMATION:
1948 : // AUTHOR Linda Lawrie
1949 : // DATE WRITTEN February 2004
1950 : // MODIFIED na
1951 : // RE-ENGINEERED na
1952 :
1953 : // PURPOSE OF THIS SUBROUTINE:
1954 : // This subroutine 'reports' the NodeConnection data structure. It groups the
1955 : // report/dump by parent, non-parent objects.
1956 :
1957 : // Using/Aliasing
1958 : using namespace DataBranchNodeConnections;
1959 :
1960 : // Formats
1961 : static constexpr std::string_view Format_702("! <#{0} Node Connections>,<Number of {0} Node Connections>\n");
1962 : static constexpr std::string_view Format_703(
1963 : "! <{} Node Connection>,<Node Name>,<Node ObjectType>,<Node ObjectName>,<Node ConnectionType>,<Node FluidStream>\n");
1964 :
1965 73 : state.dataBranchNodeConnections->NonConnectedNodes.dimension(state.dataLoopNodes->NumOfNodes, true);
1966 :
1967 73 : int NumNonParents = 0;
1968 2310 : for (int Loop = 1; Loop <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop) {
1969 2237 : if (state.dataBranchNodeConnections->NodeConnections(Loop).ObjectIsParent) continue;
1970 1559 : ++NumNonParents;
1971 : }
1972 73 : const int NumParents = state.dataBranchNodeConnections->NumOfNodeConnections - NumNonParents;
1973 73 : state.dataBranchNodeConnections->ParentNodeList.allocate(NumParents);
1974 :
1975 : // Do Parent Objects
1976 73 : print(state.files.bnd, "{}\n", "! ===============================================================");
1977 73 : print(state.files.bnd, Format_702, "Parent");
1978 73 : print(state.files.bnd, " #Parent Node Connections,{}\n", NumParents);
1979 73 : print(state.files.bnd, Format_703, "Parent");
1980 :
1981 2310 : for (int Loop = 1; Loop <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop) {
1982 2237 : if (!state.dataBranchNodeConnections->NodeConnections(Loop).ObjectIsParent) continue;
1983 678 : state.dataBranchNodeConnections->NonConnectedNodes(state.dataBranchNodeConnections->NodeConnections(Loop).NodeNumber) = false;
1984 678 : print(state.files.bnd,
1985 : " Parent Node Connection,{},{},{},{},{}\n",
1986 678 : state.dataBranchNodeConnections->NodeConnections(Loop).NodeName,
1987 : BranchNodeConnections::ConnectionObjectTypeNamesUC[static_cast<int>(
1988 678 : state.dataBranchNodeConnections->NodeConnections(Loop).ObjectType)],
1989 678 : state.dataBranchNodeConnections->NodeConnections(Loop).ObjectName,
1990 678 : DataLoopNode::ConnectionTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop).ConnectionType)],
1991 678 : state.dataBranchNodeConnections->NodeConnections(Loop).FluidStream);
1992 : // Build ParentNodeLists
1993 1075 : if ((state.dataBranchNodeConnections->NodeConnections(Loop).ConnectionType == DataLoopNode::ConnectionType::Inlet) ||
1994 397 : (state.dataBranchNodeConnections->NodeConnections(Loop).ConnectionType == DataLoopNode::ConnectionType::Outlet)) {
1995 592 : bool ParentComponentFound = false;
1996 6867 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfActualParents; ++Loop1) {
1997 6275 : if (state.dataBranchNodeConnections->ParentNodeList(Loop1).ComponentType !=
1998 8942 : state.dataBranchNodeConnections->NodeConnections(Loop).ObjectType ||
1999 2667 : state.dataBranchNodeConnections->ParentNodeList(Loop1).ComponentName !=
2000 2667 : state.dataBranchNodeConnections->NodeConnections(Loop).ObjectName)
2001 5983 : continue;
2002 292 : ParentComponentFound = true;
2003 :
2004 292 : switch (state.dataBranchNodeConnections->NodeConnections(Loop).ConnectionType) {
2005 46 : case DataLoopNode::ConnectionType::Inlet:
2006 46 : state.dataBranchNodeConnections->ParentNodeList(Loop1).InletNodeName =
2007 92 : state.dataBranchNodeConnections->NodeConnections(Loop).NodeName;
2008 46 : break;
2009 246 : case DataLoopNode::ConnectionType::Outlet:
2010 246 : state.dataBranchNodeConnections->ParentNodeList(Loop1).OutletNodeName =
2011 492 : state.dataBranchNodeConnections->NodeConnections(Loop).NodeName;
2012 246 : default:
2013 246 : break;
2014 : }
2015 : }
2016 592 : if (!ParentComponentFound) {
2017 300 : ++state.dataBranchNodeConnections->NumOfActualParents;
2018 300 : state.dataBranchNodeConnections->ParentNodeList(state.dataBranchNodeConnections->NumOfActualParents).ComponentType =
2019 300 : state.dataBranchNodeConnections->NodeConnections(Loop).ObjectType;
2020 300 : state.dataBranchNodeConnections->ParentNodeList(state.dataBranchNodeConnections->NumOfActualParents).ComponentName =
2021 600 : state.dataBranchNodeConnections->NodeConnections(Loop).ObjectName;
2022 :
2023 300 : switch (state.dataBranchNodeConnections->NodeConnections(Loop).ConnectionType) {
2024 235 : case DataLoopNode::ConnectionType::Inlet:
2025 235 : state.dataBranchNodeConnections->ParentNodeList(state.dataBranchNodeConnections->NumOfActualParents).InletNodeName =
2026 470 : state.dataBranchNodeConnections->NodeConnections(Loop).NodeName;
2027 235 : break;
2028 65 : case DataLoopNode::ConnectionType::Outlet:
2029 65 : state.dataBranchNodeConnections->ParentNodeList(state.dataBranchNodeConnections->NumOfActualParents).OutletNodeName =
2030 130 : state.dataBranchNodeConnections->NodeConnections(Loop).NodeName;
2031 65 : break;
2032 0 : default:
2033 0 : break;
2034 : }
2035 : }
2036 : }
2037 : }
2038 :
2039 : // Do non-Parent Objects
2040 73 : print(state.files.bnd, "{}\n", "! ===============================================================");
2041 73 : print(state.files.bnd, Format_702, "Non-Parent");
2042 73 : print(state.files.bnd, " #Non-Parent Node Connections,{}\n", NumNonParents);
2043 73 : print(state.files.bnd, Format_703, "Non-Parent");
2044 :
2045 2310 : for (int Loop = 1; Loop <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop) {
2046 2237 : if (state.dataBranchNodeConnections->NodeConnections(Loop).ObjectIsParent) continue;
2047 1559 : state.dataBranchNodeConnections->NonConnectedNodes(state.dataBranchNodeConnections->NodeConnections(Loop).NodeNumber) = false;
2048 1559 : print(state.files.bnd,
2049 : " Non-Parent Node Connection,{},{},{},{},{}\n",
2050 1559 : state.dataBranchNodeConnections->NodeConnections(Loop).NodeName,
2051 : BranchNodeConnections::ConnectionObjectTypeNamesUC[static_cast<int>(
2052 1559 : state.dataBranchNodeConnections->NodeConnections(Loop).ObjectType)],
2053 1559 : state.dataBranchNodeConnections->NodeConnections(Loop).ObjectName,
2054 1559 : DataLoopNode::ConnectionTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop).ConnectionType)],
2055 1559 : state.dataBranchNodeConnections->NodeConnections(Loop).FluidStream);
2056 : }
2057 :
2058 73 : int NumNonConnected = 0;
2059 862 : for (int Loop = 1; Loop <= state.dataLoopNodes->NumOfNodes; ++Loop) {
2060 789 : if (state.dataBranchNodeConnections->NonConnectedNodes(Loop)) ++NumNonConnected;
2061 : }
2062 :
2063 73 : if (NumNonConnected > 0) {
2064 0 : print(state.files.bnd, "{}\n", "! ===============================================================");
2065 : static constexpr std::string_view Format_705("! <#NonConnected Nodes>,<Number of NonConnected Nodes>\n #NonConnected Nodes,{}\n");
2066 0 : print(state.files.bnd, Format_705, NumNonConnected);
2067 : static constexpr std::string_view Format_706("! <NonConnected Node>,<NonConnected Node Number>,<NonConnected Node Name>");
2068 0 : print(state.files.bnd, "{}\n", Format_706);
2069 0 : for (int Loop = 1; Loop <= state.dataLoopNodes->NumOfNodes; ++Loop) {
2070 0 : if (!state.dataBranchNodeConnections->NonConnectedNodes(Loop)) continue;
2071 0 : print(state.files.bnd, " NonConnected Node,{},{}\n", Loop, state.dataLoopNodes->NodeID(Loop));
2072 : }
2073 : }
2074 :
2075 73 : state.dataBranchNodeConnections->NonConnectedNodes.deallocate();
2076 73 : }
2077 :
2078 73 : void ReportLoopConnections(EnergyPlusData &state)
2079 : {
2080 :
2081 : // SUBROUTINE INFORMATION:
2082 : // AUTHOR Linda Lawrie
2083 : // DATE WRITTEN December 2001
2084 : // MODIFIED March 2003; added other reporting
2085 :
2086 : // PURPOSE OF THIS SUBROUTINE:
2087 : // This subroutine reports on the node connections in various parts of the
2088 : // HVAC system: Component Sets, Air Loop, Plant and Condenser Loop, Supply and
2089 : // return air paths, controlled zones.
2090 : // This information should be useful in diagnosing node connection input errors.
2091 :
2092 : static constexpr std::string_view errstring = "**error**";
2093 :
2094 : // Formats
2095 : static constexpr std::string_view Format_700 = "! <#Component Sets>,<Number of Component Sets>";
2096 : static constexpr std::string_view Format_702 = "! <Component Set>,<Component Set Count>,<Parent Object Type>,<Parent Object Name>,<Component "
2097 : "Type>,<Component Name>,<Inlet Node ID>,<Outlet Node ID>,<Description>";
2098 : static constexpr std::string_view Format_720 = "! <#Zone Equipment Lists>,<Number of Zone Equipment Lists>";
2099 : static constexpr std::string_view Format_722 =
2100 : "! <Zone Equipment List>,<Zone Equipment List Count>,<Zone Equipment List Name>,<Zone Name>,<Number of Components>";
2101 : static constexpr std::string_view Format_723 =
2102 : "! <Zone Equipment Component>,<Component Count>,<Component Type>,<Component Name>,<Zone Name>,<Heating "
2103 : "Priority>,<Cooling Priority>";
2104 :
2105 : // Report outside air node names on the Branch-Node Details file
2106 73 : print(state.files.bnd, "{}\n", "! ===============================================================");
2107 73 : print(state.files.bnd, "{}\n", "! #Outdoor Air Nodes,<Number of Outdoor Air Nodes>");
2108 73 : print(state.files.bnd, " #Outdoor Air Nodes,{}\n", state.dataOutAirNodeMgr->NumOutsideAirNodes);
2109 73 : if (state.dataOutAirNodeMgr->NumOutsideAirNodes > 0) {
2110 26 : print(state.files.bnd, "{}\n", "! <Outdoor Air Node>,<NodeNumber>,<Node Name>");
2111 : }
2112 132 : for (int Count = 1; Count <= state.dataOutAirNodeMgr->NumOutsideAirNodes; ++Count) {
2113 59 : print(state.files.bnd,
2114 : " Outdoor Air Node,{},{}\n",
2115 59 : state.dataOutAirNodeMgr->OutsideAirNodeList(Count),
2116 59 : state.dataLoopNodes->NodeID(state.dataOutAirNodeMgr->OutsideAirNodeList(Count)));
2117 : }
2118 : // Component Sets
2119 73 : print(state.files.bnd, "{}\n", "! ===============================================================");
2120 73 : print(state.files.bnd, "{}\n", Format_700);
2121 73 : print(state.files.bnd, " #Component Sets,{}\n", state.dataBranchNodeConnections->NumCompSets);
2122 73 : print(state.files.bnd, "{}\n", Format_702);
2123 :
2124 420 : for (int Count = 1; Count <= state.dataBranchNodeConnections->NumCompSets; ++Count) {
2125 347 : print(state.files.bnd,
2126 : " Component Set,{},{},{},{},{},{},{},{}\n",
2127 : Count,
2128 : BranchNodeConnections::ConnectionObjectTypeNamesUC[static_cast<int>(
2129 347 : state.dataBranchNodeConnections->CompSets(Count).ParentObjectType)],
2130 347 : state.dataBranchNodeConnections->CompSets(Count).ParentCName,
2131 : BranchNodeConnections::ConnectionObjectTypeNamesUC[static_cast<int>(
2132 347 : state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType)],
2133 347 : state.dataBranchNodeConnections->CompSets(Count).CName,
2134 347 : state.dataBranchNodeConnections->CompSets(Count).InletNodeName,
2135 347 : state.dataBranchNodeConnections->CompSets(Count).OutletNodeName,
2136 347 : state.dataBranchNodeConnections->CompSets(Count).Description);
2137 :
2138 : std::string_view const CType = BranchNodeConnections::ConnectionObjectTypeNamesUC[static_cast<int>(
2139 347 : state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType)];
2140 347 : if (state.dataBranchNodeConnections->CompSets(Count).ParentObjectType == DataLoopNode::ConnectionObjectType::Undefined ||
2141 694 : state.dataBranchNodeConnections->CompSets(Count).InletNodeName == "UNDEFINED" ||
2142 347 : state.dataBranchNodeConnections->CompSets(Count).OutletNodeName == "UNDEFINED") {
2143 0 : if (state.dataErrTracking->AbortProcessing && state.dataSimulationManager->WarningOut) {
2144 0 : ShowWarningError(state,
2145 : "Node Connection errors shown during \"fatal error\" processing may be false because not all inputs may have "
2146 : "been retrieved.");
2147 0 : state.dataSimulationManager->WarningOut = false;
2148 : }
2149 0 : ShowWarningError(state,
2150 0 : format("Node Connection Error for object {}={}", CType, state.dataBranchNodeConnections->CompSets(Count).CName));
2151 0 : ShowContinueError(state,
2152 0 : format(" {} not on any Branch or Parent Object", state.dataBranchNodeConnections->CompSets(Count).Description));
2153 0 : ShowContinueError(state, format(" Inlet Node : {}", state.dataBranchNodeConnections->CompSets(Count).InletNodeName));
2154 0 : ShowContinueError(state, format(" Outlet Node: {}", state.dataBranchNodeConnections->CompSets(Count).OutletNodeName));
2155 0 : ++state.dataBranchNodeConnections->NumNodeConnectionErrors;
2156 0 : if (state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType ==
2157 : DataLoopNode::ConnectionObjectType::SolarCollectorUnglazedTranspired) {
2158 0 : ShowContinueError(state, "This report does not necessarily indicate a problem for a MultiSystem Transpired Collector");
2159 : }
2160 : }
2161 347 : if (state.dataBranchNodeConnections->CompSets(Count).Description == "UNDEFINED") {
2162 0 : if (state.dataErrTracking->AbortProcessing && state.dataSimulationManager->WarningOut) {
2163 0 : ShowWarningError(state,
2164 : "Node Connection errors shown during \"fatal error\" processing may be false because not all inputs may have "
2165 : "been retrieved.");
2166 0 : state.dataSimulationManager->WarningOut = false;
2167 : }
2168 0 : ShowWarningError(
2169 : state,
2170 0 : format("Potential Node Connection Error for object {}, name={}", CType, state.dataBranchNodeConnections->CompSets(Count).CName));
2171 0 : ShowContinueError(state, " Node Types are still UNDEFINED -- See Branch/Node Details file for further information");
2172 0 : ShowContinueError(state, format(" Inlet Node : {}", state.dataBranchNodeConnections->CompSets(Count).InletNodeName));
2173 0 : ShowContinueError(state, format(" Outlet Node: {}", state.dataBranchNodeConnections->CompSets(Count).OutletNodeName));
2174 0 : ++state.dataBranchNodeConnections->NumNodeConnectionErrors;
2175 : }
2176 : }
2177 :
2178 420 : for (int Count = 1; Count <= state.dataBranchNodeConnections->NumCompSets; ++Count) {
2179 3962 : for (int Count1 = Count + 1; Count1 <= state.dataBranchNodeConnections->NumCompSets; ++Count1) {
2180 3615 : if (state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType !=
2181 3615 : state.dataBranchNodeConnections->CompSets(Count1).ComponentObjectType)
2182 3615 : continue;
2183 522 : if (state.dataBranchNodeConnections->CompSets(Count).CName != state.dataBranchNodeConnections->CompSets(Count1).CName) continue;
2184 25 : if (state.dataBranchNodeConnections->CompSets(Count).InletNodeName != state.dataBranchNodeConnections->CompSets(Count1).InletNodeName)
2185 25 : continue;
2186 0 : if (state.dataBranchNodeConnections->CompSets(Count).OutletNodeName !=
2187 0 : state.dataBranchNodeConnections->CompSets(Count1).OutletNodeName)
2188 0 : continue;
2189 0 : if (state.dataErrTracking->AbortProcessing && state.dataSimulationManager->WarningOut) {
2190 0 : ShowWarningError(state,
2191 : "Node Connection errors shown during \"fatal error\" processing may be false because not all inputs may have "
2192 : "been retrieved.");
2193 0 : state.dataSimulationManager->WarningOut = false;
2194 : }
2195 : std::string_view const CType = BranchNodeConnections::ConnectionObjectTypeNamesUC[static_cast<int>(
2196 0 : state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType)];
2197 : std::string_view const ParentCType = BranchNodeConnections::ConnectionObjectTypeNamesUC[static_cast<int>(
2198 0 : state.dataBranchNodeConnections->CompSets(Count1).ParentObjectType)];
2199 : std::string_view const ParentCType1 = BranchNodeConnections::ConnectionObjectTypeNamesUC[static_cast<int>(
2200 0 : state.dataBranchNodeConnections->CompSets(Count).ParentObjectType)];
2201 0 : ShowWarningError(state, "Component plus inlet/outlet node pair used more than once:");
2202 0 : ShowContinueError(state, format(" Component : {}={}", CType, state.dataBranchNodeConnections->CompSets(Count).CName));
2203 0 : ShowContinueError(state, format(" Inlet Node : {}", state.dataBranchNodeConnections->CompSets(Count).InletNodeName));
2204 0 : ShowContinueError(state, format(" Outlet Node: {}", state.dataBranchNodeConnections->CompSets(Count).OutletNodeName));
2205 0 : ShowContinueError(state, format(" Used by : {}={}", ParentCType, state.dataBranchNodeConnections->CompSets(Count).ParentCName));
2206 0 : ShowContinueError(state, format(" and by : {}={}", ParentCType1, state.dataBranchNodeConnections->CompSets(Count1).ParentCName));
2207 0 : ++state.dataBranchNodeConnections->NumNodeConnectionErrors;
2208 : }
2209 : }
2210 : // Plant Loops
2211 73 : print(state.files.bnd, "{}\n", "! ===============================================================");
2212 73 : print(state.files.bnd, "{}\n", "! <# Plant Loops>,<Number of Plant Loops>");
2213 73 : print(state.files.bnd, " #Plant Loops,{}\n", state.dataHVACGlobal->NumPlantLoops);
2214 73 : print(state.files.bnd,
2215 : "{}\n",
2216 : "! <Plant Loop>,<Plant Loop Name>,<Loop Type>,<Inlet Node Name>,<Outlet Node Name>,<Branch List>,<Connector List>");
2217 73 : print(
2218 73 : state.files.bnd, "{}\n", "! <Plant Loop Connector>,<Connector Type>,<Connector Name>,<Loop Name>,<Loop Type>,<Number of Inlets/Outlets>");
2219 73 : print(state.files.bnd,
2220 : "{}\n",
2221 : "! <Plant Loop Connector Branches>,<Connector Node Count>,<Connector Type>,<Connector Name>,<Inlet Branch>,<Outlet Branch>,<Loop "
2222 : "Name>,<Loop Type>");
2223 73 : print(state.files.bnd,
2224 : "{}\n",
2225 : "! <Plant Loop Connector Nodes>,<Connector Node Count>,<Connector Type>,<Connector Name>,<Inlet Node>,<Outlet Node>,<Loop Name>,<Loop "
2226 : "Type>");
2227 73 : print(state.files.bnd,
2228 : "{}\n",
2229 : "! <Plant Loop Supply Connection>,<Plant Loop Name>,<Supply Side Outlet Node Name>,<Demand Side Inlet Node Name>");
2230 73 : print(state.files.bnd,
2231 : "{}\n",
2232 : "! <Plant Loop Return Connection>,<Plant Loop Name>,<Demand Side Outlet Node Name>,<Supply Side Inlet Node Name>");
2233 84 : for (int Count = 1; Count <= state.dataHVACGlobal->NumPlantLoops; ++Count) {
2234 33 : for (DataPlant::LoopSideLocation LoopSideNum : DataPlant::LoopSideKeys) {
2235 : // Plant Supply Side Loop
2236 : // LoopSideLocation::Demand and LoopSideLocation::Supply is parametrized in DataPlant
2237 22 : std::string_view const LoopString = DataPlant::DemandSupplyNames[static_cast<int>(LoopSideNum)];
2238 :
2239 22 : print(state.files.bnd,
2240 : " Plant Loop,{},{},{},{},{},{}\n",
2241 22 : state.dataPlnt->PlantLoop(Count).Name,
2242 : LoopString,
2243 22 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).NodeNameIn,
2244 22 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).NodeNameOut,
2245 22 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).BranchList,
2246 22 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).ConnectList);
2247 : // Plant Supply Side Splitter
2248 22 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.Exists) {
2249 22 : print(state.files.bnd,
2250 : " Plant Loop Connector,Splitter,{},{},{},{}\n",
2251 22 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.Name,
2252 22 : state.dataPlnt->PlantLoop(Count).Name,
2253 : LoopString,
2254 22 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.TotalOutletNodes);
2255 76 : for (int Count1 = 1; Count1 <= state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.TotalOutletNodes; ++Count1) {
2256 54 : print(state.files.bnd,
2257 : " Plant Loop Connector Branches,{},Splitter,{},",
2258 : Count1,
2259 54 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.Name);
2260 :
2261 54 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.BranchNumIn <= 0) {
2262 0 : print(state.files.bnd, "{},\n", errstring);
2263 : } else {
2264 54 : print(state.files.bnd,
2265 : "{},",
2266 54 : state.dataPlnt->PlantLoop(Count)
2267 54 : .LoopSide(LoopSideNum)
2268 54 : .Branch(state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.BranchNumIn)
2269 54 : .Name);
2270 : }
2271 :
2272 54 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.BranchNumOut(Count1) <= 0) {
2273 0 : print(state.files.bnd, "{},{},{}\n", errstring, state.dataPlnt->PlantLoop(Count).Name, LoopString);
2274 : } else {
2275 54 : print(state.files.bnd,
2276 : "{},{},{}\n",
2277 54 : state.dataPlnt->PlantLoop(Count)
2278 54 : .LoopSide(LoopSideNum)
2279 54 : .Branch(state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.BranchNumOut(Count1))
2280 54 : .Name,
2281 54 : state.dataPlnt->PlantLoop(Count).Name,
2282 : LoopString);
2283 : }
2284 :
2285 54 : print(state.files.bnd,
2286 : " Plant Loop Connector Nodes, {},Splitter,{},{},{},{},{}\n",
2287 : Count1,
2288 54 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.Name,
2289 54 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.NodeNameIn,
2290 54 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.NodeNameOut(Count1),
2291 54 : state.dataPlnt->PlantLoop(Count).Name,
2292 : LoopString);
2293 : }
2294 : }
2295 :
2296 : // Plant Supply Side Mixer
2297 22 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.Exists) {
2298 22 : print(state.files.bnd,
2299 : " Plant Loop Connector,Mixer,{},{},{},{}\n",
2300 22 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.Name,
2301 22 : state.dataPlnt->PlantLoop(Count).Name,
2302 : LoopString,
2303 22 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.TotalInletNodes); //',Supply,'// &
2304 :
2305 76 : for (int Count1 = 1; Count1 <= state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.TotalInletNodes; ++Count1) {
2306 54 : print(state.files.bnd,
2307 : " Plant Loop Connector Branches,{},Mixer,{},",
2308 : Count1,
2309 54 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.Name);
2310 54 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.BranchNumIn(Count1) <= 0) {
2311 0 : print(state.files.bnd, "{},", errstring);
2312 : } else {
2313 54 : print(state.files.bnd,
2314 : "{},",
2315 54 : state.dataPlnt->PlantLoop(Count)
2316 54 : .LoopSide(LoopSideNum)
2317 54 : .Branch(state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.BranchNumIn(Count1))
2318 54 : .Name);
2319 : }
2320 54 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.BranchNumOut <= 0) {
2321 0 : print(state.files.bnd, "{},{},Supply\n", errstring, state.dataPlnt->PlantLoop(Count).Name);
2322 : } else {
2323 54 : print(state.files.bnd,
2324 : "{},{},{}\n",
2325 54 : state.dataPlnt->PlantLoop(Count)
2326 54 : .LoopSide(LoopSideNum)
2327 54 : .Branch(state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.BranchNumOut)
2328 54 : .Name,
2329 54 : state.dataPlnt->PlantLoop(Count).Name,
2330 : LoopString);
2331 : }
2332 54 : print(state.files.bnd,
2333 : " Plant Loop Connector Nodes, {},Mixer,{},{},{},{},{}\n",
2334 : Count1,
2335 54 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.Name,
2336 54 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.NodeNameIn(Count1),
2337 54 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.NodeNameOut,
2338 54 : state.dataPlnt->PlantLoop(Count).Name,
2339 : LoopString);
2340 : }
2341 : }
2342 : }
2343 11 : print(state.files.bnd,
2344 : " Plant Loop Supply Connection,{},{},{}\n",
2345 11 : state.dataPlnt->PlantLoop(Count).Name,
2346 11 : state.dataPlnt->PlantLoop(Count).LoopSide(DataPlant::LoopSideLocation::Supply).NodeNameOut,
2347 11 : state.dataPlnt->PlantLoop(Count).LoopSide(DataPlant::LoopSideLocation::Demand).NodeNameIn);
2348 11 : print(state.files.bnd,
2349 : " Plant Loop Return Connection,{},{},{}\n",
2350 11 : state.dataPlnt->PlantLoop(Count).Name,
2351 11 : state.dataPlnt->PlantLoop(Count).LoopSide(DataPlant::LoopSideLocation::Demand).NodeNameOut,
2352 11 : state.dataPlnt->PlantLoop(Count).LoopSide(DataPlant::LoopSideLocation::Supply).NodeNameIn);
2353 :
2354 : } // Plant Demand Side Loop
2355 :
2356 : // Condenser Loops
2357 73 : print(state.files.bnd, "{}\n", "! ===============================================================");
2358 73 : print(state.files.bnd, "{}\n", "! <# Condenser Loops>,<Number of Condenser Loops>");
2359 73 : print(state.files.bnd, " #Condenser Loops,{}\n", state.dataHVACGlobal->NumCondLoops);
2360 73 : print(state.files.bnd,
2361 : "{}\n",
2362 : "! <Condenser Loop>,<Condenser Loop Name>,<Loop Type>,<Inlet Node Name>,<Outlet Node Name>,<Branch List>,<Connector List>");
2363 73 : print(state.files.bnd,
2364 : "{}\n",
2365 : "! <Condenser Loop Connector>,<Connector Type>,<Connector Name>,<Loop Name>,<Loop Type>,<Number of Inlets/Outlets>");
2366 73 : print(state.files.bnd,
2367 : "{}\n",
2368 : "! <Condenser Loop Connector Branches>,<Connector Node Count>,<Connector Type>,<Connector Name>,<Inlet Branch>,<Outlet Branch>,<Loop "
2369 : "Name>,<Loop Type>");
2370 73 : print(state.files.bnd,
2371 : "{}\n",
2372 : "! <Condenser Loop Connector Nodes>,<Connector Node Count>,<Connector Type>,<Connector Name>,<Inlet Node>,<Outlet Node>,<Loop "
2373 : "Name>,<Loop Type>");
2374 73 : print(state.files.bnd,
2375 : "{}\n",
2376 : "! <Condenser Loop Supply Connection>,<Condenser Loop Name>,<Supply Side Outlet Node Name>,<Demand Side Inlet Node Name>");
2377 73 : print(state.files.bnd,
2378 : "{}\n",
2379 : "! <Condenser Loop Return Connection>,<Condenser Loop Name>,<Demand Side Outlet Node Name>,<Supply Side Inlet Node Name>");
2380 :
2381 75 : for (int Count = state.dataHVACGlobal->NumPlantLoops + 1; Count <= state.dataPlnt->TotNumLoops; ++Count) {
2382 6 : for (DataPlant::LoopSideLocation LoopSideNum : DataPlant::LoopSideKeys) {
2383 : // Plant Supply Side Loop
2384 : // LoopSideLocation::Demand and LoopSideLocation::Supply is parametrized in DataPlant
2385 12 : const auto LoopString = [&]() {
2386 4 : if (LoopSideNum == DataPlant::LoopSideLocation::Demand) {
2387 2 : return "Demand";
2388 2 : } else if (LoopSideNum == DataPlant::LoopSideLocation::Supply) {
2389 2 : return "Supply";
2390 : } else {
2391 0 : return "";
2392 : }
2393 4 : }();
2394 :
2395 4 : print(state.files.bnd,
2396 : " Plant Loop,{},{},{},{},{},{}\n",
2397 4 : state.dataPlnt->PlantLoop(Count).Name,
2398 : LoopString,
2399 4 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).NodeNameIn,
2400 4 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).NodeNameOut,
2401 4 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).BranchList,
2402 4 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).ConnectList);
2403 : // Plant Supply Side Splitter
2404 4 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.Exists) {
2405 4 : print(state.files.bnd,
2406 : " Plant Loop Connector,Splitter,{},{},{},{}\n",
2407 4 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.Name,
2408 4 : state.dataPlnt->PlantLoop(Count).Name,
2409 : LoopString,
2410 4 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.TotalOutletNodes);
2411 15 : for (int Count1 = 1; Count1 <= state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.TotalOutletNodes; ++Count1) {
2412 11 : print(state.files.bnd,
2413 : " Plant Loop Connector Branches,{},Splitter,{},",
2414 : Count1,
2415 11 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.Name);
2416 :
2417 11 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.BranchNumIn <= 0) {
2418 0 : print(state.files.bnd, "{},", errstring);
2419 : } else {
2420 11 : print(state.files.bnd,
2421 : "{},",
2422 11 : state.dataPlnt->PlantLoop(Count)
2423 11 : .LoopSide(LoopSideNum)
2424 11 : .Branch(state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.BranchNumIn)
2425 11 : .Name);
2426 : }
2427 11 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.BranchNumOut(Count1) <= 0) {
2428 0 : print(state.files.bnd, "{},{},{}\n", errstring, state.dataPlnt->PlantLoop(Count).Name, LoopString);
2429 : } else {
2430 :
2431 11 : print(state.files.bnd,
2432 : "{},{},{}\n",
2433 11 : state.dataPlnt->PlantLoop(Count)
2434 11 : .LoopSide(LoopSideNum)
2435 11 : .Branch(state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.BranchNumOut(Count1))
2436 11 : .Name,
2437 11 : state.dataPlnt->PlantLoop(Count).Name,
2438 : LoopString);
2439 : }
2440 :
2441 11 : print(state.files.bnd,
2442 : " Plant Loop Connector Nodes, {},Splitter,{},{},{},{},{}\n",
2443 : Count1,
2444 11 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.Name,
2445 11 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.NodeNameIn,
2446 11 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Splitter.NodeNameOut(Count1),
2447 11 : state.dataPlnt->PlantLoop(Count).Name,
2448 : LoopString);
2449 : }
2450 : }
2451 :
2452 : // Plant Supply Side Mixer
2453 4 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.Exists) {
2454 4 : const int totalInletNodes = state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.TotalInletNodes;
2455 4 : print(state.files.bnd,
2456 : " Plant Loop Connector,Mixer,{},{},{},{}\n",
2457 4 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.Name,
2458 4 : state.dataPlnt->PlantLoop(Count).Name,
2459 : LoopString,
2460 : totalInletNodes); //',Supply,'// &
2461 :
2462 15 : for (int Count1 = 1; Count1 <= totalInletNodes; ++Count1) {
2463 11 : print(state.files.bnd,
2464 : " Plant Loop Connector Branches,{},Mixer,{},",
2465 : Count1,
2466 11 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.Name);
2467 :
2468 11 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.BranchNumIn(Count1) <= 0) {
2469 0 : print(state.files.bnd, "{},", errstring);
2470 : } else {
2471 11 : print(state.files.bnd,
2472 : "{},",
2473 11 : state.dataPlnt->PlantLoop(Count)
2474 11 : .LoopSide(LoopSideNum)
2475 11 : .Branch(state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.BranchNumIn(Count1))
2476 11 : .Name);
2477 : }
2478 11 : if (state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.BranchNumOut <= 0) {
2479 0 : print(state.files.bnd, "{},{},{}\n", errstring, state.dataPlnt->PlantLoop(Count).Name, LoopString);
2480 : } else {
2481 11 : print(state.files.bnd,
2482 : "{},{},{}\n",
2483 11 : state.dataPlnt->PlantLoop(Count)
2484 11 : .LoopSide(LoopSideNum)
2485 11 : .Branch(state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.BranchNumOut)
2486 11 : .Name,
2487 11 : state.dataPlnt->PlantLoop(Count).Name,
2488 : LoopString);
2489 : }
2490 11 : print(state.files.bnd,
2491 : " Plant Loop Connector Nodes, {},Mixer,{},{},{},{},{}\n",
2492 : Count1,
2493 11 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.Name,
2494 11 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.NodeNameIn(Count1),
2495 11 : state.dataPlnt->PlantLoop(Count).LoopSide(LoopSideNum).Mixer.NodeNameOut,
2496 11 : state.dataPlnt->PlantLoop(Count).Name,
2497 : LoopString);
2498 : }
2499 : }
2500 : }
2501 2 : print(state.files.bnd,
2502 : " Plant Loop Supply Connection,{},{},{}\n",
2503 2 : state.dataPlnt->PlantLoop(Count).Name,
2504 2 : state.dataPlnt->PlantLoop(Count).LoopSide(DataPlant::LoopSideLocation::Supply).NodeNameOut,
2505 2 : state.dataPlnt->PlantLoop(Count).LoopSide(DataPlant::LoopSideLocation::Demand).NodeNameIn);
2506 2 : print(state.files.bnd,
2507 : " Plant Loop Return Connection,{},{},{}\n",
2508 2 : state.dataPlnt->PlantLoop(Count).Name,
2509 2 : state.dataPlnt->PlantLoop(Count).LoopSide(DataPlant::LoopSideLocation::Demand).NodeNameOut,
2510 2 : state.dataPlnt->PlantLoop(Count).LoopSide(DataPlant::LoopSideLocation::Supply).NodeNameIn);
2511 :
2512 : } // Plant Demand Side Loop
2513 :
2514 73 : print(state.files.bnd, "{}\n", "! ===============================================================");
2515 73 : int NumOfControlledZones = 0;
2516 167 : for (int Count = 1; Count <= state.dataGlobal->NumOfZones; ++Count) {
2517 94 : if (!allocated(state.dataZoneEquip->ZoneEquipConfig)) continue;
2518 94 : if (state.dataZoneEquip->ZoneEquipConfig(Count).IsControlled) ++NumOfControlledZones;
2519 : }
2520 :
2521 73 : if (NumOfControlledZones > 0) {
2522 36 : print(state.files.bnd, "{}\n", "! <# Controlled Zones>,<Number of Controlled Zones>");
2523 36 : print(state.files.bnd, " #Controlled Zones,{}\n", NumOfControlledZones);
2524 36 : print(state.files.bnd,
2525 : "{}\n",
2526 : "! <Controlled Zone>,<Controlled Zone Name>,<Equip List Name>,<Control List Name>,<Zone Node Name>,<# Inlet Nodes>,<# Exhaust "
2527 : "Nodes>,<# Return Nodes>");
2528 36 : print(state.files.bnd,
2529 : "{}\n",
2530 : "! <Controlled Zone Inlet>,<Inlet Node Count>,<Controlled Zone Name>,<Supply Air Inlet Node Name>,<SD Sys:Cooling/Heating "
2531 : "[DD:Cooling] Inlet Node Name>,<DD Sys:Heating Inlet Node Name>");
2532 36 : print(state.files.bnd, "{}\n", "! <Controlled Zone Exhaust>,<Exhaust Node Count>,<Controlled Zone Name>,<Exhaust Air Node Name>");
2533 :
2534 91 : for (int Count = 1; Count <= state.dataGlobal->NumOfZones; ++Count) {
2535 55 : if (!state.dataZoneEquip->ZoneEquipConfig(Count).IsControlled) continue;
2536 :
2537 52 : print(state.files.bnd,
2538 : " Controlled Zone,{},{},{},{},{},{},{}\n",
2539 52 : state.dataZoneEquip->ZoneEquipConfig(Count).ZoneName,
2540 52 : state.dataZoneEquip->ZoneEquipConfig(Count).EquipListName,
2541 52 : state.dataZoneEquip->ZoneEquipConfig(Count).ControlListName,
2542 52 : state.dataLoopNodes->NodeID(state.dataZoneEquip->ZoneEquipConfig(Count).ZoneNode),
2543 52 : state.dataZoneEquip->ZoneEquipConfig(Count).NumInletNodes,
2544 52 : state.dataZoneEquip->ZoneEquipConfig(Count).NumExhaustNodes,
2545 52 : state.dataZoneEquip->ZoneEquipConfig(Count).NumReturnNodes);
2546 107 : for (int Count1 = 1; Count1 <= state.dataZoneEquip->ZoneEquipConfig(Count).NumInletNodes; ++Count1) {
2547 55 : std::string ChrName = state.dataLoopNodes->NodeID(state.dataZoneEquip->ZoneEquipConfig(Count).AirDistUnitHeat(Count1).InNode);
2548 55 : if (ChrName == "Undefined") ChrName = "N/A";
2549 55 : print(state.files.bnd,
2550 : " Controlled Zone Inlet,{},{},{},{},{}\n",
2551 : Count1,
2552 55 : state.dataZoneEquip->ZoneEquipConfig(Count).ZoneName,
2553 55 : state.dataLoopNodes->NodeID(state.dataZoneEquip->ZoneEquipConfig(Count).InletNode(Count1)),
2554 55 : state.dataLoopNodes->NodeID(state.dataZoneEquip->ZoneEquipConfig(Count).AirDistUnitCool(Count1).InNode),
2555 : ChrName);
2556 55 : }
2557 85 : for (int Count1 = 1; Count1 <= state.dataZoneEquip->ZoneEquipConfig(Count).NumExhaustNodes; ++Count1) {
2558 33 : print(state.files.bnd,
2559 : " Controlled Zone Exhaust,{},{},{}\n",
2560 : Count1,
2561 33 : state.dataZoneEquip->ZoneEquipConfig(Count).ZoneName,
2562 33 : state.dataLoopNodes->NodeID(state.dataZoneEquip->ZoneEquipConfig(Count).ExhaustNode(Count1)));
2563 : }
2564 100 : for (int Count1 = 1; Count1 <= state.dataZoneEquip->ZoneEquipConfig(Count).NumReturnNodes; ++Count1) {
2565 48 : print(state.files.bnd,
2566 : " Controlled Zone Return,{},{},{}\n",
2567 : Count1,
2568 48 : state.dataZoneEquip->ZoneEquipConfig(Count).ZoneName,
2569 48 : state.dataLoopNodes->NodeID(state.dataZoneEquip->ZoneEquipConfig(Count).ReturnNode(Count1)));
2570 : }
2571 : }
2572 :
2573 : // Report Zone Equipment Lists to BND File
2574 36 : print(state.files.bnd, "{}\n", "! ===============================================================");
2575 36 : print(state.files.bnd, "{}\n", Format_720);
2576 36 : print(state.files.bnd, " #Zone Equipment Lists,{}\n", NumOfControlledZones);
2577 36 : print(state.files.bnd, "{}\n", Format_722);
2578 36 : print(state.files.bnd, "{}\n", Format_723);
2579 :
2580 91 : for (int Count = 1; Count <= state.dataGlobal->NumOfZones; ++Count) {
2581 : // Zone equipment list array parallels controlled zone equipment array, so
2582 : // same index finds corresponding data from both arrays
2583 55 : if (!state.dataZoneEquip->ZoneEquipConfig(Count).IsControlled) continue;
2584 :
2585 52 : print(state.files.bnd,
2586 : " Zone Equipment List,{},{},{},{}\n",
2587 : Count,
2588 52 : state.dataZoneEquip->ZoneEquipList(Count).Name,
2589 52 : state.dataZoneEquip->ZoneEquipConfig(Count).ZoneName,
2590 52 : state.dataZoneEquip->ZoneEquipList(Count).NumOfEquipTypes);
2591 :
2592 117 : for (int Count1 = 1; Count1 <= state.dataZoneEquip->ZoneEquipList(Count).NumOfEquipTypes; ++Count1) {
2593 65 : print(state.files.bnd,
2594 : " Zone Equipment Component,{},{},{},{},{},{}\n",
2595 : Count1,
2596 65 : state.dataZoneEquip->ZoneEquipList(Count).EquipTypeName(Count1),
2597 65 : state.dataZoneEquip->ZoneEquipList(Count).EquipName(Count1),
2598 65 : state.dataZoneEquip->ZoneEquipConfig(Count).ZoneName,
2599 65 : state.dataZoneEquip->ZoneEquipList(Count).CoolingPriority(Count1),
2600 65 : state.dataZoneEquip->ZoneEquipList(Count).HeatingPriority(Count1));
2601 : }
2602 : }
2603 : }
2604 :
2605 : // Report Dual Duct Dampers to BND File
2606 73 : DualDuct::ReportDualDuctConnections(state);
2607 :
2608 73 : if (state.dataBranchNodeConnections->NumNodeConnectionErrors == 0) {
2609 198 : ShowMessage(state, "No node connection errors were found.");
2610 : } else {
2611 7 : if (state.dataBranchNodeConnections->NumNodeConnectionErrors > 1) {
2612 2 : ShowMessage(state, format("There were {} node connection errors noted.", state.dataBranchNodeConnections->NumNodeConnectionErrors));
2613 : } else {
2614 5 : ShowMessage(state, format("There was {} node connection error noted.", state.dataBranchNodeConnections->NumNodeConnectionErrors));
2615 : }
2616 : }
2617 :
2618 73 : state.dataErrTracking->AskForConnectionsReport = false;
2619 73 : }
2620 :
2621 1418 : void PostIPProcessing(EnergyPlusData &state)
2622 : {
2623 : // SUBROUTINE INFORMATION:
2624 : // AUTHOR Linda Lawrie
2625 : // DATE WRITTEN August 2010
2626 :
2627 : // PURPOSE OF THIS SUBROUTINE:
2628 : // This provides post processing (for errors, etc) directly after the InputProcessor
2629 : // finishes. Code originally in the Input Processor.
2630 :
2631 : // Using/Aliasing
2632 : // using SQLiteProcedures::CreateSQLiteDatabase;
2633 1418 : state.dataGlobal->DoingInputProcessing = false;
2634 :
2635 1418 : state.dataInputProcessing->inputProcessor->preProcessorCheck(
2636 1418 : state, state.dataSimulationManager->PreP_Fatal); // Check Preprocessor objects for warning, severe, etc errors.
2637 :
2638 1418 : if (state.dataSimulationManager->PreP_Fatal) {
2639 0 : ShowFatalError(state, "Preprocessor condition(s) cause termination.");
2640 : }
2641 :
2642 1418 : state.dataInputProcessing->inputProcessor->preScanReportingVariables(state);
2643 1418 : }
2644 :
2645 75 : void isInputObjectUsed(EnergyPlusData &state)
2646 : {
2647 : // there is a need to know if certain object are used in the simulation
2648 : // this may not be the best place to do this but it's a start at early reading of input data
2649 : // this concept could grow to include reading all inputs prior to the start of the simulation so all data is available
2650 : // once inputs are processed, read in all getInputs. They will be read early and will not be read again so there is no duplication
2651 :
2652 : // for example, AirLoopHVAC:DOAS systems autosize on weather data, and WeatherManager processes that data
2653 : // there is no need to process that data if there are no DOAS used in the simulation
2654 150 : state.dataGlobal->AirLoopHVACDOASUsedInSim =
2655 75 : state.dataInputProcessing->inputProcessor->getNumObjectsFound(state, "AirLoopHVAC:DedicatedOutdoorAirSystem") > 0;
2656 75 : EMSManager::CheckIfAnyEMS(state);
2657 75 : PlantManager::CheckIfAnyPlant(state);
2658 75 : PlantPipingSystemsManager::CheckIfAnySlabs(state);
2659 75 : PlantPipingSystemsManager::CheckIfAnyBasements(state);
2660 75 : SetPointManager::CheckIfAnyIdealCondEntSetPoint(state);
2661 75 : }
2662 :
2663 : } // namespace SimulationManager
2664 :
2665 : // EXTERNAL SUBROUTINES:
2666 :
2667 0 : void Resimulate(EnergyPlusData &state,
2668 : bool const ResimExt, // Flag to resimulate the exterior energy use simulation
2669 : bool const ResimHB, // Flag to resimulate the heat balance simulation (including HVAC)
2670 : bool &ResimHVAC // Flag to resimulate the HVAC simulation
2671 : )
2672 : {
2673 :
2674 : // SUBROUTINE INFORMATION:
2675 : // AUTHOR Peter Graham Ellis
2676 : // DATE WRITTEN August 2005
2677 : // MODIFIED Sep 2011 LKL/BG - resimulate only zones needing it for Radiant systems
2678 : // RE-ENGINEERED na
2679 :
2680 : // PURPOSE OF THIS SUBROUTINE:
2681 : // This subroutine is called as necessary by the Demand Manager to resimulate some of the modules that have
2682 : // already been simulated for the current timestep. For example, if LIGHTS are demand limited, the lighting
2683 : // power is reduced which also impacts the zone internal heat gains and therefore requires that the entire
2684 : // zone heat balance must be resimulated.
2685 :
2686 : // METHODOLOGY EMPLOYED:
2687 : // If the zone heat balance must be resimulated, all the major subroutines are called sequentially in order
2688 : // to recalculate the impacts of demand limiting. This routine is called from ManageHVAC _before_ any variables
2689 : // are reported or histories are updated. This routine can be called multiple times without the overall
2690 : // simulation moving forward in time.
2691 : // If only HVAC components are demand limited, then the HVAC system is resimulated, not the entire heat balance.
2692 : // Similarly, if ony exterior lights and equipment are demand limited, it is only necessary to resimulate the
2693 : // exterior energy use, not the entire heat balance, nor the HVAC system.
2694 : // Below is the hierarchy of subroutine calls. The calls marked with an asterisk are resimulated here.
2695 : // ManageSimulation
2696 : // ManageWeather
2697 : // ManageDemand
2698 : // * ManageExteriorEnergyUse
2699 : // ManageHeatBalance
2700 : // * InitHeatBalance
2701 : // PerformSolarCalculations
2702 : // ManageSurfaceHeatBalance
2703 : // * InitSurfaceHeatBalance
2704 : // ManageInternalHeatGains
2705 : // * CalcHeatBalanceOutsideSurf
2706 : // * CalcHeatBalanceInsideSurf
2707 : // ManageAirHeatBalance
2708 : // *InitAirHeatBalance
2709 : // CalcHeatBalanceAir
2710 : // * CalcAirFlow
2711 : // * ManageRefrigeratedCaseRacks
2712 : // ManageHVAC
2713 : // * ManageZoneAirUpdates 'GET ZONE SETPOINTS'
2714 : // * ManageZoneAirUpdates 'PREDICT'
2715 : // * SimHVAC
2716 : // UpdateDataandReport
2717 : // ReportAirHeatBalance
2718 : // UpdateFinalSurfaceHeatBalance
2719 : // UpdateThermalHistories
2720 : // UpdateMoistureHistories
2721 : // ManageThermalComfort
2722 : // ReportSurfaceHeatBalance
2723 : // RecKeepHeatBalance
2724 : // ReportHeatBalance
2725 :
2726 : // Using/Aliasing
2727 : using ExteriorEnergyUse::ManageExteriorEnergyUse;
2728 : using HeatBalanceAirManager::InitAirHeatBalance;
2729 : using HeatBalanceSurfaceManager::InitSurfaceHeatBalance;
2730 : using HVACManager::SimHVAC;
2731 : using RefrigeratedCase::ManageRefrigeratedCaseRacks;
2732 : using ZoneContaminantPredictorCorrector::ManageZoneContaminanUpdates;
2733 : using ZoneTempPredictorCorrector::ManageZoneAirUpdates;
2734 : using namespace ZoneEquipmentManager;
2735 :
2736 : // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
2737 0 : Real64 ZoneTempChange(0.0); // Dummy variable needed for calling ManageZoneAirUpdates
2738 :
2739 0 : if (ResimExt) {
2740 0 : ManageExteriorEnergyUse(state);
2741 :
2742 0 : ++state.dataDemandManager->DemandManagerExtIterations;
2743 : }
2744 :
2745 0 : if (ResimHB) {
2746 : // Surface simulation
2747 0 : InitSurfaceHeatBalance(state);
2748 0 : HeatBalanceSurfaceManager::CalcHeatBalanceOutsideSurf(state);
2749 0 : HeatBalanceSurfaceManager::CalcHeatBalanceInsideSurf(state);
2750 :
2751 : // Air simulation
2752 0 : InitAirHeatBalance(state);
2753 0 : ManageRefrigeratedCaseRacks(state);
2754 :
2755 0 : ++state.dataDemandManager->DemandManagerHBIterations;
2756 0 : ResimHVAC = true; // Make sure HVAC is resimulated too
2757 : }
2758 :
2759 0 : if (ResimHVAC) {
2760 : // HVAC simulation
2761 0 : ManageZoneAirUpdates(state,
2762 : DataHeatBalFanSys::PredictorCorrectorCtrl::GetZoneSetPoints,
2763 : ZoneTempChange,
2764 : false,
2765 0 : state.dataHVACGlobal->UseZoneTimeStepHistory,
2766 : 0.0);
2767 0 : if (state.dataContaminantBalance->Contaminant.SimulateContaminants)
2768 0 : ManageZoneContaminanUpdates(
2769 0 : state, DataHeatBalFanSys::PredictorCorrectorCtrl::GetZoneSetPoints, false, state.dataHVACGlobal->UseZoneTimeStepHistory, 0.0);
2770 0 : CalcAirFlowSimple(
2771 0 : state, 0, state.dataHeatBal->ZoneAirMassFlow.AdjustZoneMixingFlow, state.dataHeatBal->ZoneAirMassFlow.AdjustZoneInfiltrationFlow);
2772 0 : ManageZoneAirUpdates(
2773 0 : state, DataHeatBalFanSys::PredictorCorrectorCtrl::PredictStep, ZoneTempChange, false, state.dataHVACGlobal->UseZoneTimeStepHistory, 0.0);
2774 0 : if (state.dataContaminantBalance->Contaminant.SimulateContaminants)
2775 0 : ManageZoneContaminanUpdates(
2776 0 : state, DataHeatBalFanSys::PredictorCorrectorCtrl::PredictStep, false, state.dataHVACGlobal->UseZoneTimeStepHistory, 0.0);
2777 0 : SimHVAC(state);
2778 :
2779 0 : ++state.dataDemandManager->DemandManagerHVACIterations;
2780 : }
2781 0 : }
2782 :
2783 : } // namespace EnergyPlus
|