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 : // ObjexxFCL Headers
49 : #include <ObjexxFCL/Array.functions.hh>
50 : #include <ObjexxFCL/member.functions.hh>
51 : #include <ObjexxFCL/string.functions.hh>
52 :
53 : // EnergyPlus Headers
54 : #include <EnergyPlus/BranchNodeConnections.hh>
55 : #include <EnergyPlus/Data/EnergyPlusData.hh>
56 : #include <EnergyPlus/DataBranchNodeConnections.hh>
57 : #include <EnergyPlus/DataLoopNode.hh>
58 : #include <EnergyPlus/NodeInputManager.hh>
59 : #include <EnergyPlus/UtilityRoutines.hh>
60 :
61 : namespace EnergyPlus::BranchNodeConnections {
62 :
63 : // Module containing the routines dealing with the Branch/Node Connections (CompSets, etc)
64 :
65 : // MODULE INFORMATION:
66 : // AUTHOR Linda Lawrie
67 : // DATE WRITTEN May 2005
68 :
69 : // PURPOSE OF THIS MODULE:
70 : // This module encapsulates the connection data necessary for some of the checks
71 : // needed in the branch-node data
72 :
73 : // Using/Aliasing
74 : using namespace DataLoopNode;
75 : using namespace DataBranchNodeConnections;
76 :
77 : static constexpr std::string_view undefined("UNDEFINED");
78 :
79 : constexpr std::array<std::string_view, static_cast<int>(DataLoopNode::ConnectionObjectType::Num)> ConnectionObjectTypeNames = {
80 : "Undefined",
81 : "AirConditioner:VariableRefrigerantFlow",
82 : "AirLoopHVAC",
83 : "AirLoopHVAC:DedicatedOutdoorAirSystem",
84 : "AirLoopHVAC:ExhaustSystem",
85 : "AirLoopHVAC:Mixer",
86 : "AirLoopHVAC:OutdoorAirSystem",
87 : "AirLoopHVAC:ReturnPath",
88 : "AirLoopHVAC:ReturnPlenum",
89 : "AirLoopHVAC:Splitter",
90 : "AirLoopHVAC:SupplyPath",
91 : "AirLoopHVAC:SupplyPlenum",
92 : "AirLoopHVAC:Unitary:Furnace:HeatCool",
93 : "AirLoopHVAC:Unitary:Furnace:HeatOnly",
94 : "AirLoopHVAC:UnitaryHeatCool",
95 : "AirLoopHVAC:UnitaryHeatCool:VAVChangeoverBypass",
96 : "AirLoopHVAC:UnitaryHeatOnly",
97 : "AirLoopHVAC:UnitaryHeatPump:AirToAir",
98 : "AirLoopHVAC:UnitaryHeatPump:AirToAir:MultiSpeed",
99 : "AirLoopHVAC:UnitaryHeatPump:WaterToAir",
100 : "AirLoopHVAC:UnitarySystem",
101 : "AirLoopHVAC:ZoneMixer",
102 : "AirLoopHVAC:ZoneSplitter",
103 : "AirTerminal:DualDuct:ConstantVolume",
104 : "AirTerminal:DualDuct:ConstantVolume:Cool",
105 : "AirTerminal:DualDuct:ConstantVolume:Heat",
106 : "AirTerminal:DualDuct:VAV",
107 : "AirTerminal:DualDuct:VAV:Cool",
108 : "AirTerminal:DualDuct:VAV:Heat",
109 : "AirTerminal:DualDuct:VAV:OutdoorAir",
110 : "AirTerminal:DualDuct:VAV:OutdoorAir:OutdoorAir",
111 : "AirTerminal:DualDuct:VAV:OutdoorAir:RecirculatedAir",
112 : "AirTerminal:SingleDuct:ConstantVolume:CooledBeam",
113 : "AirTerminal:SingleDuct:ConstantVolume:FourPipeBeam",
114 : "AirTerminal:SingleDuct:ConstantVolume:FourPipeInduction",
115 : "AirTerminal:SingleDuct:ConstantVolume:NoReheat",
116 : "AirTerminal:SingleDuct:ConstantVolume:Reheat",
117 : "AirTerminal:SingleDuct:Mixer",
118 : "AirTerminal:SingleDuct:ParallelPIU:Reheat",
119 : "AirTerminal:SingleDuct:SeriesPIU:Reheat",
120 : "AirTerminal:SingleDuct:UserDefined",
121 : "AirTerminal:SingleDuct:VAV:HeatAndCool:NoReheat",
122 : "AirTerminal:SingleDuct:VAV:HeatAndCool:Reheat",
123 : "AirTerminal:SingleDuct:VAV:NoReheat",
124 : "AirTerminal:SingleDuct:VAV:Reheat",
125 : "AirTerminal:SingleDuct:VAV:Reheat:VariableSpeedFan",
126 : "AvailabilityManager:DifferentialThermostat",
127 : "AvailabilityManager:HighTemperatureTurnOff",
128 : "AvailabilityManager:HighTemperatureTurnOn",
129 : "AvailabilityManager:LowTemperatureTurnOff",
130 : "AvailabilityManager:LowTemperatureTurnOn",
131 : "Boiler:HotWater",
132 : "Boiler:Steam",
133 : "Branch",
134 : "CentralHeatPumpSystem",
135 : "Chiller:Absorption",
136 : "Chiller:Absorption:Indirect",
137 : "Chiller:CombustionTurbine",
138 : "Chiller:ConstantCOP",
139 : "Chiller:Electric",
140 : "Chiller:Electric:EIR",
141 : "Chiller:Electric:ReformulatedEIR",
142 : "Chiller:Electric:ASHRAE205",
143 : "Chiller:EngineDriven",
144 : "ChillerHeater:Absorption:DirectFired",
145 : "ChillerHeater:Absorption:DoubleEffect",
146 : "Coil:Cooling:DX",
147 : "Coil:Cooling:DX:CurveFit:Speed",
148 : "Coil:Cooling:DX:MultiSpeed",
149 : "Coil:Cooling:DX:SingleSpeed",
150 : "Coil:Cooling:DX:SingleSpeed:ThermalStorage",
151 : "Coil:Cooling:DX:SubcoolReheat",
152 : "Coil:Cooling:DX:TwoSpeed",
153 : "Coil:Cooling:DX:TwoStageWithHumidityControlMode",
154 : "Coil:Cooling:DX:VariableRefrigerantFlow",
155 : "Coil:Cooling:DX:VariableRefrigerantFlow:FluidTemperatureControl",
156 : "Coil:Cooling:DX:VariableSpeed",
157 : "Coil:Cooling:Water",
158 : "Coil:Cooling:Water:DetailedGeometry",
159 : "Coil:Cooling:WaterToAirHeatPump:EquationFit",
160 : "Coil:Cooling:WaterToAirHeatPump:ParameterEstimation",
161 : "Coil:Cooling:WaterToAirHeatPump:VariableSpeedEquationFit",
162 : "Coil:Heating:DX:MultiSpeed",
163 : "Coil:Heating:DX:SingleSpeed",
164 : "Coil:Heating:DX:VariableRefrigerantFlow",
165 : "Coil:Heating:DX:VariableRefrigerantFlow:FluidTemperatureControl",
166 : "Coil:Heating:DX:VariableSpeed",
167 : "Coil:Heating:Desuperheater",
168 : "Coil:Heating:Electric",
169 : "Coil:Heating:Electric:MultiStage",
170 : "Coil:Heating:Fuel",
171 : "Coil:Heating:Gas:MultiStage",
172 : "Coil:Heating:Steam",
173 : "Coil:Heating:Water",
174 : "Coil:Heating:WaterToAirHeatPump:EquationFit",
175 : "Coil:Heating:WaterToAirHeatPump:ParameterEstimation",
176 : "Coil:Heating:WaterToAirHeatPump:VariableSpeedEquationFit",
177 : "Coil:UserDefined",
178 : "Coil:WaterHeating:AirToWaterHeatPump:Pumped",
179 : "Coil:WaterHeating:AirToWaterHeatPump:VariableSpeed",
180 : "Coil:WaterHeating:AirToWaterHeatPump:Wrapped",
181 : "Coil:WaterHeating:Desuperheater",
182 : "CoilSystem:Cooling:DX",
183 : "CoilSystem:Cooling:DX:HeatExchangerAssisted",
184 : "CoilSystem:Cooling:Water",
185 : "CoilSystem:Cooling:Water:HeatExchangerAssisted",
186 : "CoilSystem:Heating:DX",
187 : "CoilSystem:IntegratedHeatPump:AirSource",
188 : "Condenser",
189 : "CondenserLoop",
190 : "Connector:Mixer",
191 : "Connector:Splitter",
192 : "Controller:OutdoorAir",
193 : "Controller:WaterCoil",
194 : "CoolingTower:SingleSpeed",
195 : "CoolingTower:TwoSpeed",
196 : "CoolingTower:VariableSpeed",
197 : "CoolingTower:VariableSpeed:Merkel",
198 : "Dehumidifier:Desiccant:NoFans",
199 : "Dehumidifier:Desiccant:System",
200 : "DistrictCooling",
201 : "DistrictHeating:Water",
202 : "DistrictHeating:Steam",
203 : "Duct",
204 : "ElectricEquipment:ITE:AirCooled",
205 : "EvaporativeCooler:Direct:CelDekPad",
206 : "EvaporativeCooler:Direct:ResearchSpecial",
207 : "EvaporativeCooler:Indirect:CelDekPad",
208 : "EvaporativeCooler:Indirect:ResearchSpecial",
209 : "EvaporativeCooler:Indirect:WetCoil",
210 : "EvaporativeFluidCooler:SingleSpeed",
211 : "EvaporativeFluidCooler:TwoSpeed",
212 : "Fan:ComponentModel",
213 : "Fan:ConstantVolume",
214 : "Fan:OnOff",
215 : "Fan:SystemModel",
216 : "Fan:VariableVolume",
217 : "Fan:ZoneExhaust",
218 : "FluidCooler:SingleSpeed",
219 : "FluidCooler:TwoSpeed",
220 : "Generator:CombustionTurbine",
221 : "Generator:FuelCell:AirSupply",
222 : "Generator:FuelCell:ExhaustGasToWaterHeatExchanger",
223 : "Generator:FuelCell:PowerModule",
224 : "Generator:FuelCell:StackCooler",
225 : "Generator:FuelCell:WaterSupply",
226 : "Generator:FuelSupply",
227 : "Generator:InternalCombustionEngine",
228 : "Generator:MicroCHP",
229 : "Generator:MicroTurbine",
230 : "GroundHeatExchanger:HorizontalTrench",
231 : "GroundHeatExchanger:Pond",
232 : "GroundHeatExchanger:Slinky",
233 : "GroundHeatExchanger:Surface",
234 : "GroundHeatExchanger:System",
235 : "HeaderedPumps:ConstantSpeed",
236 : "HeaderedPumps:VariableSpeed",
237 : "HeatExchanger:AirToAir:FlatPlate",
238 : "HeatExchanger:AirToAir:SensibleAndLatent",
239 : "HeatExchanger:Desiccant:BalancedFlow",
240 : "HeatExchanger:FluidToFluid",
241 : "HeatPump:AirToWater:FuelFired:Cooling",
242 : "HeatPump:AirToWater:FuelFired:Heating",
243 : "HeatPump:PlantLoop:EIR:Cooling",
244 : "HeatPump:PlantLoop:EIR:Heating",
245 : "HeatPump:WaterToWater:EquationFit:Cooling",
246 : "HeatPump:WaterToWater:EquationFit:Heating",
247 : "HeatPump:WaterToWater:ParameterEstimation:Cooling",
248 : "HeatPump:WaterToWater:ParameterEstimation:Heating",
249 : "Humidifier:Steam:Electric",
250 : "Humidifier:Steam:Gas",
251 : "Lights",
252 : "LoadProfile:Plant",
253 : "OutdoorAir:Mixer",
254 : "OutdoorAir:Node",
255 : "OutdoorAir:NodeList",
256 : "Pipe:Adiabatic",
257 : "Pipe:Adiabatic:Steam",
258 : "Pipe:Indoor",
259 : "Pipe:Outdoor",
260 : "Pipe:Underground",
261 : "PipingSystem:Underground:PipeCircuit",
262 : "PlantComponent:TemperatureSource",
263 : "PlantComponent:UserDefined",
264 : "PlantEquipmentOperation:ChillerHeaterChangeover",
265 : "PlantEquipmentOperation:ComponentSetpoint",
266 : "PlantEquipmentOperation:OutdoorDewpointDifference",
267 : "PlantEquipmentOperation:OutdoorDrybulbDifference",
268 : "PlantEquipmentOperation:OutdoorWetbulbDifference",
269 : "PlantEquipmentOperation:ThermalEnergyStorage",
270 : "PlantLoop",
271 : "Pump:ConstantSpeed",
272 : "Pump:ConstantVolume",
273 : "Pump:VariableSpeed",
274 : "Pump:VariableSpeed:Condensate",
275 : "Refrigeration:CompressorRack",
276 : "Refrigeration:Condenser:AirCooled",
277 : "Refrigeration:Condenser:EvaporativeCooled",
278 : "Refrigeration:Condenser:WaterCooled",
279 : "Refrigeration:GasCooler:AirCooled",
280 : "SetpointManager:Coldest",
281 : "SetpointManager:CondenserEnteringReset",
282 : "SetpointManager:CondenserEnteringReset:Ideal",
283 : "SetpointManager:FollowGroundTemperature",
284 : "SetpointManager:FollowOutdoorAirTemperature",
285 : "SetpointManager:FollowSystemNodeTemperature",
286 : "SetpointManager:MixedAir",
287 : "SetpointManager:MultiZone:Cooling:Average",
288 : "SetpointManager:MultiZone:Heating:Average",
289 : "SetpointManager:MultiZone:Humidity:Maximum",
290 : "SetpointManager:MultiZone:Humidity:Minimum",
291 : "SetpointManager:MultiZone:MaximumHumidity:Average",
292 : "SetpointManager:MultiZone:MinimumHumidity:Average",
293 : "SetpointManager:OutdoorAirPretreat",
294 : "SetpointManager:OutdoorAirReset",
295 : "SetpointManager:ReturnTemperature:ChilledWater",
296 : "SetpointManager:ReturnTemperature:HotWater",
297 : "SetpointManager:Scheduled",
298 : "SetpointManager:Scheduled:DualSetpoint",
299 : "SetpointManager:SingleZone:Cooling",
300 : "SetpointManager:SingleZone:Heating",
301 : "SetpointManager:SingleZone:Humidity:Maximum",
302 : "SetpointManager:SingleZone:Humidity:Minimum",
303 : "SetpointManager:SingleZone:OneStageCooling",
304 : "SetpointManager:SingleZone:OneStageHeating",
305 : "SetpointManager:SingleZone:Reheat",
306 : "SetpointManager:SystemNodeReset:Temperature",
307 : "SetpointManager:SystemNodeReset:Humidity",
308 : "SetpointManager:Warmest",
309 : "SetpointManager:WarmestTemperatureFlow",
310 : "SolarCollector:FlatPlate:PhotovoltaicThermal",
311 : "SolarCollector:FlatPlate:Water",
312 : "SolarCollector:IntegralCollectorStorage",
313 : "SolarCollector:UnglazedTranspired",
314 : "SurfaceProperty:LocalEnvironment",
315 : "SwimmingPool:Indoor",
316 : "TemperingValve",
317 : "ThermalStorage:ChilledWater:Mixed",
318 : "ThermalStorage:ChilledWater:Stratified",
319 : "ThermalStorage:Ice:Detailed",
320 : "ThermalStorage:Ice:Simple",
321 : "WaterHeater:HeatPump",
322 : "WaterHeater:HeatPump:PumpedCondenser",
323 : "WaterHeater:HeatPump:WrappedCondenser",
324 : "WaterHeater:Mixed",
325 : "WaterHeater:Stratified",
326 : "WaterUse:Connections",
327 : "ZoneHVAC:AirDistributionUnit",
328 : "ZoneHVAC:Baseboard:Convective:Electric",
329 : "ZoneHVAC:Baseboard:Convective:Water",
330 : "ZoneHVAC:Baseboard:RadiantConvective:Electric",
331 : "ZoneHVAC:Baseboard:RadiantConvective:Steam",
332 : "ZoneHVAC:Baseboard:RadiantConvective:Water",
333 : "ZoneHVAC:CoolingPanel:RadiantConvective:Water",
334 : "ZoneHVAC:Dehumidifier:DX",
335 : "ZoneHVAC:EnergyRecoveryVentilator",
336 : "ZoneHVAC:EquipmentConnections",
337 : "ZoneHVAC:EvaporativeCoolerUnit",
338 : "ZoneHVAC:ExhaustControl",
339 : "ZoneHVAC:ForcedAir:UserDefined",
340 : "ZoneHVAC:FourPipeFanCoil",
341 : "ZoneHVAC:HighTemperatureRadiant",
342 : "ZoneHVAC:HybridUnitaryHVAC",
343 : "ZoneHVAC:IdealLoadsAirSystem",
344 : "ZoneHVAC:LowTemperatureRadiant:ConstantFlow",
345 : "ZoneHVAC:LowTemperatureRadiant:VariableFlow",
346 : "ZoneHVAC:OutdoorAirUnit",
347 : "ZoneHVAC:PackagedTerminalAirConditioner",
348 : "ZoneHVAC:PackagedTerminalHeatPump",
349 : "ZoneHVAC:RefrigerationChillerSet",
350 : "ZoneHVAC:TerminalUnit:VariableRefrigerantFlow",
351 : "ZoneHVAC:UnitHeater",
352 : "ZoneHVAC:UnitVentilator",
353 : "ZoneHVAC:VentilatedSlab",
354 : "ZoneHVAC:WaterToAirHeatPump",
355 : "ZoneHVAC:WindowAirConditioner",
356 : "ZoneProperty:LocalEnvironment",
357 : "SpaceHVAC:EquipmentConnections",
358 : "SpaceHVAC:ZoneEquipmentSplitter",
359 : "SpaceHVAC:ZoneEquipmentMixer"};
360 :
361 : constexpr std::array<std::string_view, static_cast<int>(DataLoopNode::ConnectionObjectType::Num)> ConnectionObjectTypeNamesUC = {
362 : undefined,
363 : "AIRCONDITIONER:VARIABLEREFRIGERANTFLOW",
364 : "AIRLOOPHVAC",
365 : "AIRLOOPHVAC:DEDICATEDOUTDOORAIRSYSTEM",
366 : "AIRLOOPHVAC:EXHAUSTSYSTEM",
367 : "AIRLOOPHVAC:MIXER",
368 : "AIRLOOPHVAC:OUTDOORAIRSYSTEM",
369 : "AIRLOOPHVAC:RETURNPATH",
370 : "AIRLOOPHVAC:RETURNPLENUM",
371 : "AIALOOPHVAC:SPLITTER",
372 : "AIRLOOPHVAC:SUPPLYPATH",
373 : "AIRLOOPHVAC:SUPPLYPLENUM",
374 : "AIRLOOPHVAC:UNITARY:FURNACE:HEATCOOL",
375 : "AIRLOOPHVAC:UNITARY:FURNACE:HEATONLY",
376 : "AIRLOOPHVAC:UNITARYHEATCOOL",
377 : "AIRLOOPHVAC:UNITARYHEATCOOL:VAVCHANGEOVERBYPASS",
378 : "AIRLOOPHVAC:UNITARYHEATONLY",
379 : "AIRLOOPHVAC:UNITARYHEATPUMP:AIRTOAIR",
380 : "AIRLOOPHVAC:UNITARYHEATPUMP:AIRTOAIR:MULTISPEED",
381 : "AIRLOOPHVAC:UNITARYHEATPUMP:WATERTOAIR",
382 : "AIRLOOPHVAC:UNITARYSYSTEM",
383 : "AIRLOOPHVAC:ZONEMIXER",
384 : "AIRLOOPHVAC:ZONESPLITTER",
385 : "AIRTERMINAL:DUALDUCT:CONSTANTVOLUME",
386 : "AIRTERMINAL:DUALDUCT:CONSTANTVOLUME:COOL",
387 : "AIRTERMINAL:DUALDUCT:CONSTANTVOLUME:HEAT",
388 : "AIRTERMINAL:DUALDUCT:VAV",
389 : "AIRTERMINAL:DUALDUCT:VAV:COOL",
390 : "AIRTERMINAL:DUALDUCT:VAV:HEAT",
391 : "AIRTERMINAL:DUALDUCT:VAV:OUTDOORAIR",
392 : "AIRTERMINAL:DUALDUCT:VAV:OUTDOORAIR:OUTDOORAIR",
393 : "AIRTERMINAL:DUALDUCT:VAV:OUTDOORAIR:RECIRCULATEDAIR",
394 : "AIRTERMINAL:SINGLEDUCT:CONSTANTVOLUME:COOLEDBEAM",
395 : "AIRTERMINAL:SINGLEDUCT:CONSTANTVOLUME:FOURPIPEBEAM",
396 : "AIRTERMINAL:SINGLEDUCT:CONSTANTVOLUME:FOURPIPEINDUCTION",
397 : "AIRTERMINAL:SINGLEDUCT:CONSTANTVOLUME:NOREHEAT",
398 : "AIRTERMINAL:SINGLEDUCT:CONSTANTVOLUME:REHEAT",
399 : "AIRTERMINAL:SINGLEDUCT:MIXER",
400 : "AIRTERMINAL:SINGLEDUCT:PARALLELPIU:REHEAT",
401 : "AIRTERMINAL:SINGLEDUCT:SERIESPIU:REHEAT",
402 : "AIRTERMINAL:SINGLEDUCT:USERDEFINED",
403 : "AIRTERMINAL:SINGLEDUCT:VAV:HEATANDCOOL:NOREHEAT",
404 : "AIRTERMINAL:SINGLEDUCT:VAV:HEATANDCOOL:REHEAT",
405 : "AIRTERMINAL:SINGLEDUCT:VAV:NOREHEAT",
406 : "AIRTERMINAL:SINGLEDUCT:VAV:REHEAT",
407 : "AIRTERMINAL:SINGLEDUCT:VAV:REHEAT:VARIABLESPEEDFAN",
408 : "AVAILABILITYMANAGER:DIFFERENTIALTHERMOSTAT",
409 : "AVAILABILITYMANAGER:HIGHTEMPERATURETURNOFF",
410 : "AVAILABILITYMANAGER:HIGHTEMPERATURETURNON",
411 : "AVAILABILITYMANAGER:LOWTEMPERATURETURNOFF",
412 : "AVAILABILITYMANAGER:LOWTEMPERATURETURNON",
413 : "BOILER:HOTWATER",
414 : "BOILER:STEAM",
415 : "BRANCH",
416 : "CENTRALHEATPUMPSYSTEM",
417 : "CHILLER:ABSORPTION",
418 : "CHILLER:ABSORPTION:INDIRECT",
419 : "CHILLER:COMBUSTIONTURBINE",
420 : "CHILLER:CONSTANTCOP",
421 : "CHILLER:ELECTRIC",
422 : "CHILLER:ELECTRIC:EIR",
423 : "CHILLER:ELECTRIC:REFORMULATEDEIR",
424 : "CHILLER:ELECTRIC:ASHRAE205",
425 : "CHILLER:ENGINEDRIVEN",
426 : "CHILLERHEATER:ABSORPTION:DIRECTFIRED",
427 : "CHILLERHEATER:ABSORPTION:DOUBLEEFFECT",
428 : "COIL:COOLING:DX",
429 : "COIL:COOLING:DX:CURVEFIT:SPEED",
430 : "COIL:COOLING:DX:MULTISPEED",
431 : "COIL:COOLING:DX:SINGLESPEED",
432 : "COIL:COOLING:DX:SINGLESPEED:THERMALSTORAGE",
433 : "COIL:COOLING:DX:SUBCOOLREHEAT",
434 : "COIL:COOLING:DX:TWOSPEED",
435 : "COIL:COOLING:DX:TWOSTAGEWITHHUMIDITYCONTROLMODE",
436 : "COIL:COOLING:DX:VARIABLEREFRIGERANTFLOW",
437 : "COIL:COOLING:DX:VARIABLEREFRIGERANTFLOW:FLUIDTEMPERATURECONTROL",
438 : "COIL:COOLING:DX:VARIABLESPEED",
439 : "COIL:COOLING:WATER",
440 : "COIL:COOLING:WATER:DETAILEDGEOMETRY",
441 : "COIL:COOLING:WATERTOAIRHEATPUMP:EQUATIONFIT",
442 : "COIL:COOLING:WATERTOAIRHEATPUMP:PARAMETERESTIMATION",
443 : "COIL:COOLING:WATERTOAIRHEATPUMP:VARIABLESPEEDEQUATIONFIT",
444 : "COIL:HEATING:DX:MULTISPEED",
445 : "COIL:HEATING:DX:SINGLESPEED",
446 : "COIL:HEATING:DX:VARIABLEREFRIGERANTFLOW",
447 : "COIL:HEATING:DX:VARIABLEREFRIGERANTFLOW:FLUIDTEMPERATURECONTROL",
448 : "COIL:HEATING:DX:VARIABLESPEED",
449 : "COIL:HEATING:DESUPERHEATER",
450 : "COIL:HEATING:ELECTRIC",
451 : "COIL:HEATING:ELECTRIC:MULTISTAGE",
452 : "COIL:HEATING:FUEL",
453 : "COIL:HEATING:GAS:MULTISTAGE",
454 : "COIL:HEATING:STEAM",
455 : "COIL:HEATING:WATER",
456 : "COIL:HEATING:WATERTOAIRHEATPUMP:EQUATIONFIT",
457 : "COIL:HEATING:WATERTOAIRHEATPUMP:PARAMETERESTIMATION",
458 : "COIL:HEATING:WATERTOAIRHEATPUMP:VARIABLESPEEDEQUATIONFIT",
459 : "COIL:USERDEFINED",
460 : "COIL:WATERHEATING:AIRTOWATERHEATPUMP:PUMPED",
461 : "COIL:WATERHEATING:AIRTOWATERHEATPUMP:VARIABLESPEED",
462 : "COIL:WATERHEATING:AIRTOWATERHEATPUMP:WRAPPED",
463 : "COIL:WATERHEATING:DESUPERHEATER",
464 : "COILSYSTEM:COOLING:DX",
465 : "COILSYSTEM:COOLING:DX:HEATEXCHANGERASSISTED",
466 : "COILSYSTEM:COOLING:WATER",
467 : "COILSYSTEM:COOLING:WATER:HEATEXCHANGERASSISTED",
468 : "COILSYSTEM:HEATING:DX",
469 : "COILSYSTEM:INTEGRATEDHEATPUMP:AIRSOURCE",
470 : "CONDENSER",
471 : "CONDENSERLOOP",
472 : "CONNECTOR:MIXER",
473 : "CONNECTOR:SPLITTER",
474 : "CONTROLLER:OUTDOORAIR",
475 : "CONTROLLER:WATERCOIL",
476 : "COOLINGTOWER:SINGLESPEED",
477 : "COOLINGTOWER:TWOSPEED",
478 : "COOLINGTOWER:VARIABLESPEED",
479 : "COOLINGTOWER:VARIABLESPEED:MERKEL",
480 : "DEHUMIDIFIER:DESICCANT:NOFANS",
481 : "DEHUMIDIFIER:DESICCANT:SYSTEM",
482 : "DISTRICTCOOLING",
483 : "DISTRICTHEATING:WATER",
484 : "DISTRICTHEATING:STEAM",
485 : "DUCT",
486 : "ELECTRICEQUIPMENT:ITE:AIRCOOLED",
487 : "EVAPORATIVECOOLER:DIRECT:CELDEKPAD",
488 : "EVAPORATIVECOOLER:DIRECT:RESEARCHSPECIAL",
489 : "EVAPORATIVECOOLER:INDIRECT:CELDEKPAD",
490 : "EVAPORATIVECOOLER:INDIRECT:RESEARCHSPECIAL",
491 : "EVAPORATIVECOOLER:INDIRECT:WETCOIL",
492 : "EVAPORATIVEFLUIDCOOLER:SINGLESPEED",
493 : "EVAPORATIVEFLUIDCOOLER:TWOSPEED",
494 : "FAN:COMPONENTMODEL",
495 : "FAN:CONSTANTVOLUME",
496 : "FAN:ONOFF",
497 : "FAN:SYSTEMMODEL",
498 : "FAN:VARIABLEVOLUME",
499 : "FAN:ZONEEXHAUST",
500 : "FLUIDCOOLER:SINGLESPEED",
501 : "FLUIDCOOLER:TWOSPEED",
502 : "GENERATOR:COMBUSTIONTURBINE",
503 : "GENERATOR:FUELCELL:AIRSUPPLY",
504 : "GENERATOR:FUELCELL:EXHAUSTGASTOWATERHEATEXCHANGER",
505 : "GENERATOR:FUELCELL:POWERMODULE",
506 : "GENERATOR:FUELCELL:STACKCOOLER",
507 : "GENERATOR:FUELCELL:WATERSUPPLY",
508 : "GENERATOR:FUELSUPPLY",
509 : "GENERATOR:INTERNALCOMBUSTIONENGINE",
510 : "GENERATOR:MICROCHP",
511 : "GENERATOR:MICROTURBINE",
512 : "GROUNDHEATEXCHANGER:HORIZONTALTRENCH",
513 : "GROUNDHEATEXCHANGER:POND",
514 : "GROUNDHEATEXCHANGER:SLINKY",
515 : "GROUNDHEATEXCHANGER:SURFACE",
516 : "GROUNDHEATEXCHANGER:SYSTEM",
517 : "HEADEREDPUMPS:CONSTANTSPEED",
518 : "HEADEREDPUMPS:VARIABLESPEED",
519 : "HEATEXCHANGER:AIRTOAIR:FLATPLATE",
520 : "HEATEXCHANGER:AIRTOAIR:SENSIBLEANDLATENT",
521 : "HEATEXCHANGER:DESICCANT:BALANCEDFLOW",
522 : "HEATEXCHANGER:FLUIDTOFLUID",
523 : "HEATPUMP:AIRTOWATER:FUELFIRED:COOLING",
524 : "HEATPUMP:AIRTOWATER:FUELFIRED:HEATING",
525 : "HEATPUMP:PLANTLOOP:EIR:COOLING",
526 : "HEATPUMP:PLANTLOOP:EIR:HEATING",
527 : "HEATPUMP:WATERTOWATER:EQUATIONFIT:COOLING",
528 : "HEATPUMP:WATERTOWATER:EQUATIONFIT:HEATING",
529 : "HEATPUMP:WATERTOWATER:PARAMETERESTIMATION:COOLING",
530 : "HEATPUMP:WATERTOWATER:PARAMETERESTIMATION:HEATING",
531 : "HUMIDIFIER:STEAM:ELECTRIC",
532 : "HUMIDIFIER:STEAM:GAS",
533 : "LIGHTS",
534 : "LOADPROFILE:PLANT",
535 : "OUTDOORAIR:MIXER",
536 : "OUTDOORAIR:NODE",
537 : "OUTDOORAIR:NODELIST",
538 : "PIPE:ADIABATIC",
539 : "PIPE:ADIABATIC:STEAM",
540 : "PIPE:INDOOR",
541 : "PIPE:OUTDOOR",
542 : "PIPE:UNDERGROUND",
543 : "PIPINGSYSTEM:UNDERGROUND:PIPECIRCUIT",
544 : "PLANTCOMPONENT:TEMPERATURESOURCE",
545 : "PLANTCOMPONENT:USERDEFINED",
546 : "PLANTEQUIPMENTOPERATION:CHILLERHEATERCHANGEOVER",
547 : "PLANTEQUIPMENTOPERATION:COMPONENTSETPOINT",
548 : "PLANTEQUIPMENTOPERATION:OUTDOORDEWPOINTDIFFERENCE",
549 : "PLANTEQUIPMENTOPERATION:OUTDOORDRYBULBDIFFERENCE",
550 : "PLANTEQUIPMENTOPERATION:OUTDOORWETBULBDIFFERENCE",
551 : "PLANTEQUIPMENTOPERATION:THERMALENERGYSTORAGE",
552 : "PLANTLOOP",
553 : "PUMP:CONSTANTSPEED",
554 : "PUMP:CONSTANTVOLUME",
555 : "PUMP:VARIABLESPEED",
556 : "PUMP:VARIABLESPEED:CONDENSATE",
557 : "REFRIGERATION:COMPRESSORRACK",
558 : "REFRIGERATION:CONDENSER:AIRCOOLED",
559 : "REFRIGERATION:CONDENSER:EVAPORATIVECOOLED",
560 : "REFRIGERATION:CONDENSER:WATERCOOLED",
561 : "REFRIGERATION:GASCOOLER:AIRCOOLED",
562 : "SETPOINTMANAGER:COLDEST",
563 : "SETPOINTMANAGER:CONDENSERENTERINGRESET",
564 : "SETPOINTMANAGER:CONDENSERENTERINGRESET:IDEAL",
565 : "SETPOINTMANAGER:FOLLOWGROUNDTEMPERATURE",
566 : "SETPOINTMANAGER:FOLLOWOUTDOORAIRTEMPERATURE",
567 : "SETPOINTMANAGER:FOLLOWSYSTEMNODETEMPERATURE",
568 : "SETPOINTMANAGER:MIXEDAIR",
569 : "SETPOINTMANAGER:MULTIZONE:COOLING:AVERAGE",
570 : "SETPOINTMANAGER:MULTIZONE:HEATING:AVERAGE",
571 : "SETPOINTMANAGER:MULTIZONE:HUMIDITY:MAXIMUM",
572 : "SETPOINTMANAGER:MULTIZONE:HUMIDITY:MINIMUM",
573 : "SETPOINTMANAGER:MULTIZONE:MAXIMUMHUMIDITY:AVERAGE",
574 : "SETPOINTMANAGER:MULTIZONE:MINIMUMHUMIDITY:AVERAGE",
575 : "SETPOINTMANAGER:OUTDOORAIRPRETREAT",
576 : "SETPOINTMANAGER:OUTDOORAIRRESET",
577 : "SETPOINTMANAGER:RETURNTEMPERATURE:CHILLEDWATER",
578 : "SETPOINTMANAGER:RETURNTEMPERATURE:HOTWATER",
579 : "SETPOINTMANAGER:SCHEDULED",
580 : "SETPOINTMANAGER:SCHEDULED:DUALSETPOINT",
581 : "SETPOINTMANAGER:SINGLEZONE:COOLING",
582 : "SETPOINTMANAGER:SINGLEZONE:HEATING",
583 : "SETPOINTMANAGER:SINGLEZONE:HUMIDITY:MAXIMUM",
584 : "SETPOINTMANAGER:SINGLEZONE:HUMIDITY:MINIMUM",
585 : "SETPOINTMANAGER:SINGLEZONE:ONESTAGECOOLING",
586 : "SETPOINTMANAGER:SINGLEZONE:ONESTAGEHEATING",
587 : "SETPOINTMANAGER:SINGLEZONE:REHEAT",
588 : "SETPOINTMANAGER:SYSTEMNODERESET:TEMPERATURE",
589 : "SETPOINTMANAGER:SYSTEMNODERESET:HUMIDITY",
590 : "SETPOINTMANAGER:WARMEST",
591 : "SETPOINTMANAGER:WARMESTTEMPERATUREFLOW",
592 : "SOLARCOLLECTOR:FLATPLATE:PHOTOVOLTAICTHERMAL",
593 : "SOLARCOLLECTOR:FLATPLATE:WATER",
594 : "SOLARCOLLECTOR:INTEGRALCOLLECTORSTORAGE",
595 : "SOLARCOLLECTOR:UNGLAZEDTRANSPIRED",
596 : "SURFACEPROPERTY:LOCALENVIRONMENT",
597 : "SWIMMINGPOOL:INDOOR",
598 : "TEMPERINGVALVE",
599 : "THERMALSTORAGE:CHILLEDWATER:MIXED",
600 : "THERMALSTORAGE:CHILLEDWATER:STRATIFIED",
601 : "THERMALSTORAGE:ICE:DETAILED",
602 : "THERMALSTORAGE:ICE:SIMPLE",
603 : "WATERHEATER:HEATPUMP",
604 : "WATERHEATER:HEATPUMP:PUMPEDCONDENSER",
605 : "WATERHEATER:HEATPUMP:WRAPPEDCONDENSER",
606 : "WATERHEATER:MIXED",
607 : "WATERHEATER:STRATIFIED",
608 : "WATERUSE:CONNECTIONS",
609 : "ZONEHVAC:AIRDISTRIBUTIONUNIT",
610 : "ZONEHVAC:BASEBOARD:CONVECTIVE:ELECTRIC",
611 : "ZONEHVAC:BASEBOARD:CONVECTIVE:WATER",
612 : "ZONEHVAC:BASEBOARD:RADIANTCONVECTIVE:ELECTRIC",
613 : "ZONEHVAC:BASEBOARD:RADIANTCONVECTIVE:STEAM",
614 : "ZONEHVAC:BASEBOARD:RADIANTCONVECTIVE:WATER",
615 : "ZONEHVAC:COOLINGPANEL:RADIANTCONVECTIVE:WATER",
616 : "ZONEHVAC:DEHUMIDIFIER:DX",
617 : "ZONEHVAC:ENERGYRECOVERYVENTILATOR",
618 : "ZONEHVAC:EQUIPMENTCONNECTIONS",
619 : "ZONEHVAC:EVAPORATIVECOOLERUNIT",
620 : "ZONEHVAC:EXHAUSTCONTROL",
621 : "ZONEHVAC:FORCEDAIR:USERDEFINED",
622 : "ZONEHVAC:FOURPIPEFANCOIL",
623 : "ZONEHVAC:HIGHTEMPERATURERADIANT",
624 : "ZONEHVAC:HYBRIDUNITARYHVAC",
625 : "ZONEHVAC:IDEALLOADSAIRSYSTEM",
626 : "ZONEHVAC:LOWTEMPERATURERADIANT:CONSTANTFLOW",
627 : "ZONEHVAC:LOWTEMPERATURERADIANT:VARIABLEFLOW",
628 : "ZONEHVAC:OUTDOORAIRUNIT",
629 : "ZONEHVAC:PACKAGEDTERMINALAIRCONDITIONER",
630 : "ZONEHVAC:PACKAGEDTERMINALHEATPUMP",
631 : "ZONEHVAC:REFRIGERATIONCHILLERSET",
632 : "ZONEHVAC:TERMINALUNIT:VARIABLEREFRIGERANTFLOW",
633 : "ZONEHVAC:UNITHEATER",
634 : "ZONEHVAC:UNITVENTILATOR",
635 : "ZONEHVAC:VENTILATEDSLAB",
636 : "ZONEHVAC:WATERTOAIRHEATPUMP",
637 : "ZONEHVAC:WINDOWAIRCONDITIONER",
638 : "ZONEPROPERTY:LOCALENVIRONMENT",
639 : "SPACEHVAC:EQUIPMENTCONNECTIONS",
640 : "SPACEHVAC:ZONEEQUIPMENTSPLITTER",
641 : "SPACEHVAC:ZONEEQUIPMENTMIXER"};
642 :
643 305269 : void RegisterNodeConnection(EnergyPlusData &state,
644 : int const NodeNumber, // Number for this Node
645 : std::string_view const NodeName, // Name of this Node
646 : DataLoopNode::ConnectionObjectType const ObjectType, // Type of object this Node is connected to (e.g. Chiller:Electric)
647 : std::string_view const ObjectName, // Name of object this Node is connected to (e.g. MyChiller)
648 : DataLoopNode::ConnectionType const ConnectionType, // Connection Type for this Node (must be valid)
649 : NodeInputManager::CompFluidStream const FluidStream, // Count on Fluid Streams
650 : bool const IsParent, // True when node is a parent node
651 : bool &errFlag, // Will be True if errors already detected or if errors found here
652 : std::string_view const InputFieldName // Input Field Name
653 : )
654 : {
655 :
656 : // SUBROUTINE INFORMATION:
657 : // AUTHOR Linda K. Lawrie
658 : // DATE WRITTEN February 2004
659 : // MODIFIED na
660 : // RE-ENGINEERED na
661 :
662 : // PURPOSE OF THIS SUBROUTINE:
663 : // This subroutine registers a node connection in the Node Connection data structure. This
664 : // structure is intended to help with HVAC diagramming as well as validation of nodes.
665 :
666 : // SUBROUTINE PARAMETER DEFINITIONS:
667 : static constexpr std::string_view RoutineName = "RegisterNodeConnection: ";
668 :
669 305269 : bool ErrorsFoundHere = false;
670 :
671 305269 : if ((ObjectType == DataLoopNode::ConnectionObjectType::Invalid) || (ObjectType == DataLoopNode::ConnectionObjectType::Num)) {
672 0 : ShowSevereError(state, "Developer Error: Invalid ObjectType");
673 0 : ShowContinueError(state, format("Occurs for Node={}, ObjectName={}", std::string{NodeName}, std::string{ObjectName}));
674 0 : ErrorsFoundHere = true;
675 : }
676 :
677 305269 : std::string_view const objTypeStr = ConnectionObjectTypeNames[static_cast<int>(ObjectType)];
678 305269 : std::string_view const conTypeStr = ConnectionTypeNames[static_cast<int>(ConnectionType)];
679 :
680 305269 : if ((ConnectionType == DataLoopNode::ConnectionType::Invalid) || (ConnectionType == DataLoopNode::ConnectionType::Num)) {
681 0 : ShowSevereError(state, format("{}{}{}", RoutineName, "Invalid ConnectionType=", ConnectionType));
682 0 : ShowContinueError(state, format("Occurs for Node={}, ObjectType={}, ObjectName={}", NodeName, objTypeStr, ObjectName));
683 0 : ErrorsFoundHere = true;
684 : }
685 :
686 305269 : bool MakeNew = true;
687 116058361 : for (int Count = 1; Count <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Count) {
688 115753092 : if (state.dataBranchNodeConnections->NodeConnections(Count).NodeNumber != NodeNumber) {
689 115409940 : continue;
690 : }
691 343152 : if (state.dataBranchNodeConnections->NodeConnections(Count).ObjectType != ObjectType) {
692 213244 : continue;
693 : }
694 129908 : if (!Util::SameString(state.dataBranchNodeConnections->NodeConnections(Count).ObjectName, ObjectName)) {
695 8819 : continue;
696 : }
697 121089 : if (state.dataBranchNodeConnections->NodeConnections(Count).ConnectionType != ConnectionType) {
698 2402 : continue;
699 : }
700 118687 : if (state.dataBranchNodeConnections->NodeConnections(Count).FluidStream != FluidStream) {
701 1 : continue;
702 : }
703 237372 : if ((state.dataBranchNodeConnections->NodeConnections(Count).ObjectIsParent && !IsParent) ||
704 118686 : (!state.dataBranchNodeConnections->NodeConnections(Count).ObjectIsParent && IsParent)) {
705 0 : ShowSevereError(state, format("{}{}", RoutineName, "Node registered for both Parent and \"not\" Parent"));
706 0 : ShowContinueError(state, format("{}{}{}{}{}{}", "Occurs for Node=", NodeName, ", ObjectType=", ObjectType, ", ObjectName=", ObjectName));
707 0 : ErrorsFoundHere = true;
708 : }
709 118686 : MakeNew = false;
710 : }
711 305269 : if (MakeNew) {
712 186583 : int constexpr NodeConnectionAlloc = 1000;
713 186583 : ++state.dataBranchNodeConnections->NumOfNodeConnections;
714 372431 : if (state.dataBranchNodeConnections->NumOfNodeConnections > 1 &&
715 185848 : state.dataBranchNodeConnections->NumOfNodeConnections > state.dataBranchNodeConnections->MaxNumOfNodeConnections) {
716 37 : state.dataBranchNodeConnections->NodeConnections.resize(state.dataBranchNodeConnections->MaxNumOfNodeConnections += NodeConnectionAlloc);
717 186546 : } else if (state.dataBranchNodeConnections->NumOfNodeConnections == 1) {
718 735 : state.dataBranchNodeConnections->NodeConnections.allocate(NodeConnectionAlloc);
719 735 : state.dataBranchNodeConnections->MaxNumOfNodeConnections = NodeConnectionAlloc;
720 : }
721 :
722 186583 : state.dataBranchNodeConnections->NodeConnections(state.dataBranchNodeConnections->NumOfNodeConnections).NodeNumber = NodeNumber;
723 186583 : state.dataBranchNodeConnections->NodeConnections(state.dataBranchNodeConnections->NumOfNodeConnections).NodeName = NodeName;
724 186583 : state.dataBranchNodeConnections->NodeConnections(state.dataBranchNodeConnections->NumOfNodeConnections).ObjectType = ObjectType;
725 186583 : state.dataBranchNodeConnections->NodeConnections(state.dataBranchNodeConnections->NumOfNodeConnections).ObjectName = ObjectName;
726 186583 : state.dataBranchNodeConnections->NodeConnections(state.dataBranchNodeConnections->NumOfNodeConnections).ConnectionType = ConnectionType;
727 186583 : state.dataBranchNodeConnections->NodeConnections(state.dataBranchNodeConnections->NumOfNodeConnections).FluidStream = FluidStream;
728 186583 : state.dataBranchNodeConnections->NodeConnections(state.dataBranchNodeConnections->NumOfNodeConnections).ObjectIsParent = IsParent;
729 : }
730 :
731 305269 : if (has_prefixi(objTypeStr, "AirTerminal:")) {
732 10208 : if (!InputFieldName.empty()) {
733 10208 : ++state.dataBranchNodeConnections->NumOfAirTerminalNodes;
734 10208 : int constexpr EqNodeConnectionAlloc = 100;
735 19867 : if (state.dataBranchNodeConnections->NumOfAirTerminalNodes > 1 &&
736 9659 : state.dataBranchNodeConnections->NumOfAirTerminalNodes > state.dataBranchNodeConnections->MaxNumOfAirTerminalNodes) {
737 21 : state.dataBranchNodeConnections->AirTerminalNodeConnections.resize(state.dataBranchNodeConnections->MaxNumOfAirTerminalNodes +=
738 : EqNodeConnectionAlloc);
739 10187 : } else if (state.dataBranchNodeConnections->NumOfAirTerminalNodes == 1) {
740 549 : state.dataBranchNodeConnections->AirTerminalNodeConnections.allocate(EqNodeConnectionAlloc);
741 549 : state.dataBranchNodeConnections->MaxNumOfAirTerminalNodes = EqNodeConnectionAlloc;
742 : }
743 :
744 : // Check out AirTerminal inlet/outlet nodes
745 30624 : bool Found = Util::FindItemInList(NodeName,
746 10208 : state.dataBranchNodeConnections->AirTerminalNodeConnections,
747 : &EqNodeConnectionDef::NodeName,
748 10208 : state.dataBranchNodeConnections->NumOfAirTerminalNodes - 1);
749 10208 : if (Found != 0) { // Nodename already used
750 0 : ShowSevereError(state, fmt::format("{}{}=\"{}\" node name duplicated", RoutineName, ObjectType, ObjectName));
751 0 : ShowContinueError(state, format("NodeName=\"{}\", entered as type={}", NodeName, conTypeStr));
752 0 : ShowContinueError(state, fmt::format("In Field={}", InputFieldName));
753 0 : ShowContinueError(state,
754 0 : format("NodeName=\"{}\", entered as type={}", NodeName, ConnectionTypeNamesUC[static_cast<int>(ConnectionType)]));
755 0 : ShowContinueError(state, format("In Field={}", InputFieldName));
756 0 : ShowContinueError(
757 : state,
758 0 : format("Already used in {}=\"{}\".", objTypeStr, state.dataBranchNodeConnections->AirTerminalNodeConnections(Found).ObjectName));
759 0 : ShowContinueError(
760 : state,
761 0 : format(" as type={}, In Field={}",
762 0 : ConnectionTypeNamesUC[static_cast<int>(state.dataBranchNodeConnections->AirTerminalNodeConnections(Found).ConnectionType)],
763 0 : state.dataBranchNodeConnections->AirTerminalNodeConnections(Found).InputFieldName));
764 0 : ErrorsFoundHere = true;
765 : } else {
766 10208 : state.dataBranchNodeConnections->AirTerminalNodeConnections(state.dataBranchNodeConnections->NumOfAirTerminalNodes).NodeName =
767 10208 : NodeName;
768 10208 : state.dataBranchNodeConnections->AirTerminalNodeConnections(state.dataBranchNodeConnections->NumOfAirTerminalNodes).ObjectType =
769 : ObjectType;
770 10208 : state.dataBranchNodeConnections->AirTerminalNodeConnections(state.dataBranchNodeConnections->NumOfAirTerminalNodes).ObjectName =
771 10208 : ObjectName;
772 10208 : state.dataBranchNodeConnections->AirTerminalNodeConnections(state.dataBranchNodeConnections->NumOfAirTerminalNodes).ConnectionType =
773 : ConnectionType;
774 10208 : state.dataBranchNodeConnections->AirTerminalNodeConnections(state.dataBranchNodeConnections->NumOfAirTerminalNodes).InputFieldName =
775 10208 : InputFieldName;
776 : }
777 : } else {
778 0 : ShowSevereError(state, fmt::format("{}{} , Developer Error: Input Field Name not included.", RoutineName, objTypeStr));
779 0 : ShowContinueError(state, "Node names not checked for duplication.");
780 : }
781 : }
782 :
783 305269 : if (ErrorsFoundHere) {
784 0 : errFlag = true;
785 : }
786 305269 : }
787 :
788 24 : void OverrideNodeConnectionType(
789 : EnergyPlusData &state,
790 : int const NodeNumber, // Number for this Node
791 : std::string const &NodeName, // Name of this Node
792 : DataLoopNode::ConnectionObjectType const ObjectType, // Type of object this Node is connected to (e.g. Chiller:Electric)
793 : std::string const &ObjectName, // Name of object this Node is connected to (e.g. MyChiller)
794 : DataLoopNode::ConnectionType const ConnectionType, // Connection Type for this Node (must be valid)
795 : NodeInputManager::CompFluidStream const FluidStream, // Count on Fluid Streams
796 : bool const IsParent, // True when node is a parent node
797 : bool &errFlag // Will be True if errors already detected or if errors found here
798 : )
799 : {
800 :
801 : // SUBROUTINE INFORMATION:
802 : // AUTHOR M. J. Witte
803 : // DATE WRITTEN June 2016
804 :
805 : // PURPOSE:
806 : // This subroutine modifies an existing node connection in the Node Connection data structure. This
807 : // structure is intended to help with HVAC diagramming as well as validation of nodes. This function
808 : // is a based on RegisterNodeConnection.
809 :
810 : static constexpr std::string_view RoutineName("ModifyNodeConnectionType: ");
811 :
812 24 : if ((ConnectionType == DataLoopNode::ConnectionType::Invalid) || (ConnectionType == DataLoopNode::ConnectionType::Num)) {
813 0 : ShowSevereError(state, format("{}{}{}", RoutineName, "Invalid ConnectionType=", ConnectionType));
814 0 : ShowContinueError(
815 : state,
816 0 : format("Occurs for Node={}, ObjectType={}, ObjectName={}", NodeName, ConnectionTypeNames[static_cast<int>(ObjectType)], ObjectName));
817 0 : errFlag = true;
818 : }
819 :
820 24 : int Found = 0;
821 1572 : for (int Count = 1; Count <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Count) {
822 1572 : if (state.dataBranchNodeConnections->NodeConnections(Count).NodeNumber != NodeNumber) {
823 1507 : continue;
824 : }
825 65 : if (state.dataBranchNodeConnections->NodeConnections(Count).ObjectType != ObjectType) {
826 19 : continue;
827 : }
828 46 : if (!Util::SameString(state.dataBranchNodeConnections->NodeConnections(Count).ObjectName, ObjectName)) {
829 22 : continue;
830 : }
831 24 : if (state.dataBranchNodeConnections->NodeConnections(Count).FluidStream != FluidStream) {
832 0 : continue;
833 : }
834 24 : if ((state.dataBranchNodeConnections->NodeConnections(Count).ObjectIsParent != IsParent)) {
835 0 : continue;
836 : }
837 24 : Found = Count;
838 24 : break;
839 : }
840 :
841 24 : if (Found > 0) {
842 24 : state.dataBranchNodeConnections->NodeConnections(Found).ConnectionType = ConnectionType;
843 : } else {
844 0 : ShowSevereError(state, format("{}{}", RoutineName, "Existing node connection not found."));
845 0 : ShowContinueError(
846 : state,
847 0 : format("Occurs for Node={}, ObjectType={}, ObjectName={}", NodeName, ConnectionTypeNames[static_cast<int>(ObjectType)], ObjectName));
848 0 : errFlag = true;
849 : }
850 24 : }
851 :
852 782 : void CheckNodeConnections(EnergyPlusData &state, bool &ErrorsFound)
853 : {
854 :
855 : // SUBROUTINE INFORMATION:
856 : // AUTHOR Linda Lawrie
857 : // DATE WRITTEN March 2004
858 : // MODIFIED na
859 : // RE-ENGINEERED na
860 :
861 : // PURPOSE OF THIS SUBROUTINE:
862 : // This subroutine processes the node connection data structure looking at:
863 : // 1. In the NodeConnections list, for any node which appears as a sensor or an
864 : // actuator, the same node must also appear in the connections list at least once
865 : // as a node type which is not sensor or actuator or outsideair.
866 : // 2. In the NodeConnections list, for any node which appears as a setpoint, the
867 : // same node must also appear in the connections list at least once as a node type
868 : // which is not a setpoint or outsideair.
869 : // 3. Every ZoneInlet must appear as an outlet from something, otherwise it will
870 : // do nothing.
871 : // 4. Every ZoneExhaust must appear as an inlet to something,
872 : // otherwise it will do nothing.
873 : // 5. Every inlet node should match either an Outlet, ZoneReturn, ZoneExhaust, ReliefAir,
874 : // or OutsideAir node.
875 : // With the current data structure, when checking inlets:
876 : // a) If an InletNode's object is AirLoopHVAC, CondenserLoop, or PlantLoop, then skip the test.
877 : // b) If an InletNode's object is not one of the above types, it is valid if the
878 : // same node name appears as an INLET to an AirLoopHVAC, CondenserLoop, or PlantLoop.
879 : // 6. Any given node can only be an inlet once in the list of Non-Parent Node Connections
880 : // 7. Any given node can only be an outlet once in the list of Non-Parent Node Connections
881 : // 8. non-parent outlet nodes -- must never be an outlet more than once
882 : // 9. nodes of type OutsideAirReference must be registered as DataLoopNode::NodeConnectionType::OutsideAir
883 : // 10. fluid streams cannot have multiple inlet/outlet nodes on same component
884 : // 11. zone nodes may not be used as anything else except as a setpoint, sensor or actuator node
885 :
886 : // METHODOLOGY EMPLOYED:
887 : // Needs description, as appropriate.
888 :
889 : // Using/Aliasing
890 :
891 : // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
892 : bool IsValid;
893 : bool IsInlet;
894 : bool IsOutlet;
895 : bool MatchedAtLeastOne;
896 : int ErrorCounter;
897 782 : Array1D_int FluidStreamInletCount;
898 782 : Array1D_int FluidStreamOutletCount;
899 782 : Array1D_int NodeObjects;
900 782 : Array1D_bool FluidStreamCounts;
901 :
902 782 : ErrorCounter = 0;
903 :
904 : // Check 1 -- check sensor and actuator nodes
905 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
906 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::Sensor) {
907 165497 : continue;
908 : }
909 9373 : IsValid = false;
910 8267104 : for (int Loop2 = 1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
911 8257731 : if (Loop1 == Loop2) {
912 9373 : continue;
913 : }
914 8248358 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).NodeNumber !=
915 8248358 : state.dataBranchNodeConnections->NodeConnections(Loop2).NodeNumber) {
916 8203845 : continue;
917 : }
918 88987 : if ((state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Actuator) ||
919 44474 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Sensor)) {
920 10109 : continue;
921 : }
922 :
923 34404 : IsValid = true;
924 : }
925 9373 : if (!IsValid) {
926 0 : ShowSevereError(state,
927 0 : format("Node Connection Error, Node=\"{}\", Sensor node did not find a matching node of appropriate type (other than "
928 : "Actuator or Sensor).",
929 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName));
930 :
931 0 : ShowContinueError(state,
932 0 : format("Reference Object={}, Name={}",
933 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
934 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
935 0 : ++ErrorCounter;
936 0 : ErrorsFound = true;
937 : }
938 : }
939 :
940 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
941 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::Actuator) {
942 172016 : continue;
943 : }
944 2854 : IsValid = false;
945 2898305 : for (int Loop2 = 1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
946 2895451 : if (Loop1 == Loop2) {
947 2854 : continue;
948 : }
949 2892597 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).NodeNumber !=
950 2892597 : state.dataBranchNodeConnections->NodeConnections(Loop2).NodeNumber) {
951 2886913 : continue;
952 : }
953 :
954 5684 : if ((state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Actuator) ||
955 11329 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Sensor) ||
956 5645 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::OutsideAir)) {
957 1044 : continue;
958 : }
959 :
960 4640 : IsValid = true;
961 : }
962 2854 : if (!IsValid) {
963 0 : ShowSevereError(state,
964 0 : format("Node Connection Error, Node=\"{}\", Actuator node did not find a matching node of appropriate type (other than "
965 : "Actuator, Sensor, OutsideAir).",
966 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName));
967 :
968 0 : ShowContinueError(state,
969 0 : format("Reference Object={}, Name={}",
970 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
971 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
972 0 : ++ErrorCounter;
973 0 : ErrorsFound = true;
974 : }
975 : }
976 :
977 : // Check 2 -- setpoint nodes
978 : // Check 2a -- setpoint node must also be an inlet or an outlet (CR8212)
979 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
980 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::SetPoint) {
981 170068 : continue;
982 : }
983 4802 : IsValid = false;
984 4802 : IsInlet = false;
985 4802 : IsOutlet = false;
986 3165622 : for (int Loop2 = 1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
987 3160820 : if (Loop1 == Loop2) {
988 4802 : continue;
989 : }
990 3156018 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).NodeNumber !=
991 3156018 : state.dataBranchNodeConnections->NodeConnections(Loop2).NodeNumber) {
992 3133994 : continue;
993 : }
994 43842 : if ((state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::SetPoint) ||
995 21818 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::OutsideAir)) {
996 206 : continue;
997 : }
998 :
999 21818 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Inlet) {
1000 3324 : IsInlet = true;
1001 18494 : } else if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Outlet) {
1002 9912 : IsOutlet = true;
1003 : }
1004 21818 : IsValid = true;
1005 : }
1006 4802 : if (!IsValid) {
1007 0 : ShowSevereError(state,
1008 0 : format("Node Connection Error, Node=\"{}\", Setpoint node did not find a matching node of appropriate type (other than "
1009 : "Setpoint, OutsideAir).",
1010 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName));
1011 :
1012 0 : ShowContinueError(state,
1013 0 : format("Reference Object={}, Name={}",
1014 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1015 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1016 0 : ++ErrorCounter;
1017 0 : ErrorsFound = true;
1018 : }
1019 4802 : if (!IsInlet && !IsOutlet) {
1020 0 : ShowSevereError(state,
1021 0 : format("Node Connection Error, Node=\"{}\", Setpoint node did not find a matching node of type Inlet or Outlet.",
1022 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName));
1023 0 : ShowContinueError(state, "It appears this node is not part of the HVAC system.");
1024 :
1025 0 : ShowContinueError(state,
1026 0 : format("Reference Object={}, Name={}",
1027 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1028 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1029 0 : ++ErrorCounter;
1030 : }
1031 : }
1032 :
1033 : // Check 2a -- setpoint node must also be an inlet or an outlet (CR8212)
1034 :
1035 : // Check 3 -- zone inlet nodes -- must be an outlet somewhere
1036 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
1037 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::ZoneInlet) {
1038 170477 : continue;
1039 : }
1040 4393 : IsValid = false;
1041 5685376 : for (int Loop2 = 1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
1042 5680983 : if (Loop1 == Loop2) {
1043 4393 : continue;
1044 : }
1045 5676590 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).NodeNumber !=
1046 5676590 : state.dataBranchNodeConnections->NodeConnections(Loop2).NodeNumber) {
1047 5665171 : continue;
1048 : }
1049 11419 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType != DataLoopNode::ConnectionType::Outlet) {
1050 595 : continue;
1051 : }
1052 10824 : IsValid = true;
1053 : }
1054 4393 : if (!IsValid) {
1055 0 : ShowSevereError(state,
1056 0 : format("Node Connection Error, Node=\"{}\", ZoneInlet node did not find an outlet node.",
1057 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName));
1058 :
1059 0 : ShowContinueError(state,
1060 0 : format("Reference Object={}, Name={}",
1061 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1062 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1063 0 : ++ErrorCounter;
1064 : }
1065 : }
1066 :
1067 : // Check 4 -- zone exhaust nodes -- must be an inlet somewhere
1068 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
1069 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::ZoneExhaust) {
1070 173923 : continue;
1071 : }
1072 947 : IsValid = false;
1073 2035968 : for (int Loop2 = 1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
1074 2035021 : if (Loop1 == Loop2) {
1075 947 : continue;
1076 : }
1077 2034074 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).NodeNumber !=
1078 2034074 : state.dataBranchNodeConnections->NodeConnections(Loop2).NodeNumber) {
1079 2032389 : continue;
1080 : }
1081 1685 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType != DataLoopNode::ConnectionType::Inlet) {
1082 14 : continue;
1083 : }
1084 1671 : IsValid = true;
1085 : }
1086 947 : if (!IsValid) {
1087 0 : ShowSevereError(state,
1088 0 : format("Node Connection Error, Node=\"{}\", ZoneExhaust node did not find a matching inlet node.",
1089 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName));
1090 :
1091 0 : ShowContinueError(state,
1092 0 : format("Reference Object={}, Name={}",
1093 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1094 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1095 0 : ++ErrorCounter;
1096 : }
1097 : }
1098 :
1099 : // Check 5 -- return plenum induced air outlet nodes -- must be an inlet somewhere
1100 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
1101 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::InducedAir) {
1102 174844 : continue;
1103 : }
1104 26 : IsValid = false;
1105 17817 : for (int Loop2 = 1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
1106 17791 : if (Loop1 == Loop2) {
1107 26 : continue;
1108 : }
1109 17765 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).NodeNumber !=
1110 17765 : state.dataBranchNodeConnections->NodeConnections(Loop2).NodeNumber) {
1111 17718 : continue;
1112 : }
1113 47 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType != DataLoopNode::ConnectionType::Inlet) {
1114 0 : continue;
1115 : }
1116 47 : IsValid = true;
1117 : }
1118 26 : if (!IsValid) {
1119 0 : ShowSevereError(state,
1120 0 : format("Node Connection Error, Node=\"{}\", Return plenum induced air outlet node did not find a matching inlet node.",
1121 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName));
1122 :
1123 0 : ShowContinueError(state,
1124 0 : format("Reference Object={}, Name={}",
1125 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1126 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1127 0 : ++ErrorCounter;
1128 0 : ErrorsFound = true;
1129 : }
1130 : }
1131 :
1132 : // Check 6 -- every inlet should have a matching outlet, zonereturn, zoneexhaust, induced air, reliefair or outsideair
1133 : // a) If an InletNode's object is AirLoopHVAC, CondenserLoop, or PlantLoop, then skip the test.
1134 : // b) If an InletNode's object is not one of the above types, it is valid if the
1135 : // same node name appears as an INLET to an AirLoopHVAC, CondenserLoop, or PlantLoop.
1136 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
1137 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::Inlet) {
1138 108369 : continue;
1139 : }
1140 66501 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType == DataLoopNode::ConnectionObjectType::AirLoopHVAC ||
1141 130172 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType == DataLoopNode::ConnectionObjectType::CondenserLoop ||
1142 63671 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType == DataLoopNode::ConnectionObjectType::PlantLoop) {
1143 4542 : continue;
1144 : }
1145 61959 : IsValid = false;
1146 61959 : MatchedAtLeastOne = false;
1147 68311543 : for (int Loop2 = 1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
1148 68249584 : if (Loop1 == Loop2) {
1149 61959 : continue;
1150 : }
1151 68187625 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).NodeNumber !=
1152 68187625 : state.dataBranchNodeConnections->NodeConnections(Loop2).NodeNumber) {
1153 68062243 : continue;
1154 : }
1155 :
1156 125382 : if ((state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Outlet) ||
1157 68422 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::ZoneReturn) ||
1158 64985 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::ZoneExhaust) ||
1159 63314 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::InducedAir) ||
1160 257023 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::ReliefAir) ||
1161 63219 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::OutsideAir)) {
1162 64219 : MatchedAtLeastOne = true;
1163 64219 : continue;
1164 : }
1165 :
1166 105715 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Inlet &&
1167 44552 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectType == DataLoopNode::ConnectionObjectType::AirLoopHVAC ||
1168 39854 : state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectType == DataLoopNode::ConnectionObjectType::CondenserLoop ||
1169 38838 : state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectType == DataLoopNode::ConnectionObjectType::PlantLoop)) {
1170 9138 : MatchedAtLeastOne = true;
1171 9138 : continue;
1172 : }
1173 52025 : IsValid = false;
1174 : }
1175 61959 : if (!IsValid && !MatchedAtLeastOne) {
1176 4 : ShowSevereError(state,
1177 4 : format("{}{}{}",
1178 : "Node Connection Error, Node=\"",
1179 2 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName,
1180 : R"(", Inlet node did not find an appropriate matching "outlet" node.)"));
1181 4 : ShowContinueError(state, "If this is an outdoor air inlet node, it must be listed in an OutdoorAir:Node or OutdoorAir:NodeList object.");
1182 :
1183 4 : ShowContinueError(state,
1184 4 : format("Reference Object={}, Name={}",
1185 2 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1186 2 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1187 2 : ++ErrorCounter;
1188 : }
1189 : }
1190 :
1191 : // Check 7 -- non-parent inlet nodes -- must never be an inlet more than once
1192 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
1193 : // Only non-parent node connections
1194 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectIsParent) {
1195 53847 : continue;
1196 : }
1197 121023 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::Inlet) {
1198 76833 : continue;
1199 : }
1200 17978022 : for (int Loop2 = Loop1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
1201 17933833 : if (Loop1 == Loop2) {
1202 44190 : continue;
1203 : }
1204 17889643 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectIsParent) {
1205 2872520 : continue;
1206 : }
1207 15017123 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType != DataLoopNode::ConnectionType::Inlet) {
1208 8201645 : continue;
1209 : }
1210 6815478 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).NodeNumber ==
1211 6815478 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeNumber) {
1212 2 : ShowSevereError(state,
1213 2 : format("Node Connection Error, Node=\"{}\", The same node appears as a non-parent Inlet node more than once.",
1214 1 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName));
1215 :
1216 2 : ShowContinueError(
1217 : state,
1218 2 : format("Reference Object={}, Name={}",
1219 1 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1220 1 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1221 :
1222 2 : ShowContinueError(
1223 : state,
1224 2 : format("Reference Object={}, Name={}",
1225 1 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectType)],
1226 1 : state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectName));
1227 1 : ++ErrorCounter;
1228 1 : break;
1229 : }
1230 : }
1231 : }
1232 :
1233 : // Check 8 -- non-parent outlet nodes -- must never be an outlet more than once
1234 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
1235 : // Only non-parent node connections
1236 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectIsParent) {
1237 53847 : continue;
1238 : }
1239 121023 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::Outlet) {
1240 78129 : continue;
1241 : }
1242 42894 : IsValid = true;
1243 18138218 : for (int Loop2 = Loop1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
1244 18095325 : if (Loop1 == Loop2) {
1245 42894 : continue;
1246 : }
1247 18052431 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectIsParent) {
1248 2885844 : continue;
1249 : }
1250 15166587 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType != DataLoopNode::ConnectionType::Outlet) {
1251 8905610 : continue;
1252 : }
1253 6260977 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).NodeNumber ==
1254 6260977 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeNumber) {
1255 : // Skip if one of the
1256 2 : ShowSevereError(state,
1257 2 : format("Node Connection Error, Node=\"{}\", The same node appears as a non-parent Outlet node more than once.",
1258 1 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName));
1259 :
1260 2 : ShowContinueError(
1261 : state,
1262 2 : format("Reference Object={}, Name={}",
1263 1 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1264 1 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1265 :
1266 2 : ShowContinueError(
1267 : state,
1268 2 : format("Reference Object={}, Name={}",
1269 1 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectType)],
1270 1 : state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectName));
1271 :
1272 1 : ++ErrorCounter;
1273 1 : break;
1274 : }
1275 : }
1276 : }
1277 :
1278 : // Check 9 -- nodes of type OutsideAirReference must be registered as DataLoopNode::NodeConnectionType::OutsideAir
1279 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
1280 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::OutsideAirReference) {
1281 174348 : continue;
1282 : }
1283 522 : IsValid = false;
1284 161380 : for (int Loop2 = 1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
1285 161380 : if (Loop1 == Loop2) {
1286 29 : continue;
1287 : }
1288 161351 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).NodeNumber !=
1289 161351 : state.dataBranchNodeConnections->NodeConnections(Loop2).NodeNumber) {
1290 160819 : continue;
1291 : }
1292 532 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType != DataLoopNode::ConnectionType::OutsideAir) {
1293 10 : continue;
1294 : }
1295 522 : IsValid = true;
1296 522 : break;
1297 : }
1298 522 : if (!IsValid) {
1299 0 : ShowSevereError(state,
1300 0 : format("{}{}{}",
1301 : "Node Connection Error, Node=\"",
1302 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName,
1303 : R"(", Outdoor Air Reference did not find an appropriate "outdoor air" node.)"));
1304 0 : ShowContinueError(state, "This node must be listed in an OutdoorAir:Node or OutdoorAir:NodeList object in order to set its conditions.");
1305 :
1306 0 : ShowContinueError(state,
1307 0 : format("Reference Object={}, Name={}",
1308 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1309 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1310 :
1311 0 : ++ErrorCounter;
1312 : }
1313 : }
1314 :
1315 : // Check 10 -- fluid streams cannot have multiple inlet/outlet nodes on same component
1316 : // can have multiple inlets with one outlet or vice versa but cannot have multiple both inlet and outlet
1317 782 : if (state.dataBranchNodeConnections->NumOfNodeConnections > 0) {
1318 714 : int MaxFluidStream = static_cast<int>(maxval(state.dataBranchNodeConnections->NodeConnections, &NodeConnectionDef::FluidStream));
1319 714 : FluidStreamInletCount.allocate(MaxFluidStream);
1320 714 : FluidStreamOutletCount.allocate(MaxFluidStream);
1321 714 : FluidStreamCounts.allocate(MaxFluidStream);
1322 714 : NodeObjects.allocate(state.dataBranchNodeConnections->NumOfNodeConnections + 1);
1323 714 : FluidStreamInletCount = 0;
1324 714 : FluidStreamOutletCount = 0;
1325 714 : NodeObjects = 0;
1326 714 : FluidStreamCounts = false;
1327 : // Following code relies on node connections for single object type/name being grouped together
1328 714 : int Object = 1;
1329 714 : int EndConnect = 0;
1330 714 : int NumObjects = 2;
1331 714 : NodeObjects(1) = 1;
1332 174870 : while (Object < state.dataBranchNodeConnections->NumOfNodeConnections) {
1333 174156 : if (state.dataBranchNodeConnections->NodeConnections(Object).ObjectType !=
1334 329862 : state.dataBranchNodeConnections->NodeConnections(Object + 1).ObjectType ||
1335 155706 : state.dataBranchNodeConnections->NodeConnections(Object).ObjectName !=
1336 155706 : state.dataBranchNodeConnections->NodeConnections(Object + 1).ObjectName) {
1337 64860 : EndConnect = Object + 1;
1338 64860 : NodeObjects(NumObjects) = EndConnect;
1339 : // if (Object + 1 < state.dataBranchNodeConnections->NumOfNodeConnections) ++NumObjects;
1340 64860 : ++NumObjects;
1341 : }
1342 174156 : ++Object;
1343 : }
1344 714 : NodeObjects(NumObjects) = state.dataBranchNodeConnections->NumOfNodeConnections + 1;
1345 : // NodeObjects now contains each consecutive object...
1346 66288 : for (Object = 1; Object <= NumObjects - 1; ++Object) {
1347 65574 : IsValid = true;
1348 65574 : FluidStreamInletCount = 0;
1349 65574 : FluidStreamOutletCount = 0;
1350 65574 : FluidStreamCounts = false;
1351 65574 : int Loop1 = NodeObjects(Object);
1352 65574 : if (state.dataBranchNodeConnections->NumOfNodeConnections < 2) {
1353 0 : continue;
1354 : }
1355 65574 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectIsParent) {
1356 24739 : continue;
1357 : }
1358 40835 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType == DataLoopNode::ConnectionType::Inlet) {
1359 22084 : ++FluidStreamInletCount(static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).FluidStream));
1360 18751 : } else if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType == DataLoopNode::ConnectionType::Outlet) {
1361 7172 : ++FluidStreamOutletCount(static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).FluidStream));
1362 : }
1363 122933 : for (int Loop2 = Loop1 + 1; Loop2 <= NodeObjects(Object + 1) - 1; ++Loop2) {
1364 82098 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectIsParent) {
1365 2066 : continue;
1366 : }
1367 80032 : if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Inlet) {
1368 22102 : ++FluidStreamInletCount(static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop2).FluidStream));
1369 57930 : } else if (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Outlet) {
1370 35722 : ++FluidStreamOutletCount(static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop2).FluidStream));
1371 : }
1372 : }
1373 681760 : for (int Loop2 = 1; Loop2 <= MaxFluidStream; ++Loop2) {
1374 640925 : if (FluidStreamInletCount(Loop2) > 1 && FluidStreamOutletCount(Loop2) > 1) {
1375 0 : IsValid = false;
1376 0 : FluidStreamCounts(Loop2) = true;
1377 : }
1378 : }
1379 40835 : if (!IsValid) {
1380 :
1381 0 : ShowSevereError(
1382 : state,
1383 0 : format("(Developer) Node Connection Error, Object={}:{}",
1384 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1385 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1386 :
1387 0 : ShowContinueError(state, "Object has multiple connections on both inlet and outlet fluid streams.");
1388 0 : for (int Loop2 = 1; Loop2 <= MaxFluidStream; ++Loop2) {
1389 0 : if (FluidStreamCounts(Loop2)) {
1390 0 : ShowContinueError(state, format("...occurs in Fluid Stream [{}].", Loop2));
1391 : }
1392 : }
1393 0 : ++ErrorCounter;
1394 0 : ErrorsFound = true;
1395 : }
1396 : }
1397 714 : FluidStreamInletCount.deallocate();
1398 714 : FluidStreamOutletCount.deallocate();
1399 714 : FluidStreamCounts.deallocate();
1400 714 : NodeObjects.deallocate();
1401 : }
1402 :
1403 : // Check 11 - zone nodes may not be used as anything else except as a setpoint, sensor or actuator node
1404 175652 : for (int Loop1 = 1; Loop1 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop1) {
1405 174870 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).ConnectionType != DataLoopNode::ConnectionType::ZoneNode) {
1406 170452 : continue;
1407 : }
1408 4418 : IsValid = true;
1409 3287430 : for (int Loop2 = Loop1; Loop2 <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop2) {
1410 3283012 : if (Loop1 == Loop2) {
1411 4418 : continue;
1412 : }
1413 3278594 : if (state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName ==
1414 3278594 : state.dataBranchNodeConnections->NodeConnections(Loop2).NodeName) {
1415 :
1416 636 : if ((state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Actuator) ||
1417 636 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::Sensor) ||
1418 0 : (state.dataBranchNodeConnections->NodeConnections(Loop2).ConnectionType == DataLoopNode::ConnectionType::SetPoint)) {
1419 636 : continue;
1420 : }
1421 :
1422 0 : ShowSevereError(state,
1423 0 : format("Node Connection Error, Node Name=\"{}\", The same zone node appears more than once.",
1424 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).NodeName));
1425 :
1426 0 : ShowContinueError(
1427 : state,
1428 0 : format("Reference Object={}, Object Name={}",
1429 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectType)],
1430 0 : state.dataBranchNodeConnections->NodeConnections(Loop1).ObjectName));
1431 :
1432 0 : ShowContinueError(
1433 : state,
1434 0 : format("Reference Object={}, Object Name={}",
1435 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectType)],
1436 0 : state.dataBranchNodeConnections->NodeConnections(Loop2).ObjectName));
1437 :
1438 0 : ++ErrorCounter;
1439 0 : ErrorsFound = true;
1440 : }
1441 : }
1442 : }
1443 :
1444 782 : state.dataBranchNodeConnections->NumNodeConnectionErrors += ErrorCounter;
1445 782 : }
1446 :
1447 58413 : bool IsParentObject(EnergyPlusData &state, DataLoopNode::ConnectionObjectType const ComponentType, std::string const &ComponentName)
1448 : {
1449 :
1450 : // FUNCTION INFORMATION:
1451 : // AUTHOR Linda Lawrie
1452 : // DATE WRITTEN May 2005
1453 :
1454 : // PURPOSE OF THIS FUNCTION:
1455 : // This routine determines if a component name is a parent node.
1456 :
1457 : // METHODOLOGY EMPLOYED:
1458 : // Traverses CompSet structure.
1459 :
1460 : // Return value
1461 58413 : bool IsParent = false; // True if this combination is a parent
1462 :
1463 44435454 : for (int Loop = 1; Loop <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Loop) {
1464 46116920 : if (state.dataBranchNodeConnections->NodeConnections(Loop).ObjectType == ComponentType &&
1465 1686373 : state.dataBranchNodeConnections->NodeConnections(Loop).ObjectName == ComponentName) {
1466 53506 : if (state.dataBranchNodeConnections->NodeConnections(Loop).ObjectIsParent) {
1467 22300 : IsParent = true;
1468 : }
1469 53506 : break;
1470 : }
1471 : }
1472 58413 : if (!IsParent) {
1473 36113 : IsParent = IsParentObjectCompSet(state, ComponentType, ComponentName);
1474 : }
1475 :
1476 58413 : return IsParent;
1477 : }
1478 :
1479 8714 : int WhichParentSet(EnergyPlusData &state, DataLoopNode::ConnectionObjectType const ComponentType, std::string const &ComponentName)
1480 : {
1481 :
1482 : // FUNCTION INFORMATION:
1483 : // AUTHOR Linda Lawrie
1484 : // DATE WRITTEN May 2005
1485 :
1486 : // PURPOSE OF THIS FUNCTION:
1487 : // This routine determines which parent node list (number) for a given component name
1488 : // and type.
1489 :
1490 : // Return value
1491 8714 : int WhichOne = 0;
1492 :
1493 1103002 : for (int Loop = 1; Loop <= state.dataBranchNodeConnections->NumOfActualParents; ++Loop) {
1494 1217026 : if (state.dataBranchNodeConnections->ParentNodeList(Loop).ComponentType == ComponentType &&
1495 115464 : state.dataBranchNodeConnections->ParentNodeList(Loop).ComponentName == ComponentName) {
1496 7274 : WhichOne = Loop;
1497 7274 : break;
1498 : }
1499 : }
1500 :
1501 8714 : return WhichOne;
1502 : }
1503 :
1504 8714 : void GetParentData(EnergyPlusData &state,
1505 : DataLoopNode::ConnectionObjectType const ComponentType,
1506 : std::string const &ComponentName,
1507 : std::string &InletNodeName,
1508 : int &InletNodeNum,
1509 : std::string &OutletNodeName,
1510 : int &OutletNodeNum,
1511 : bool &ErrorsFound)
1512 : {
1513 :
1514 : // SUBROUTINE INFORMATION:
1515 : // AUTHOR Linda Lawrie
1516 : // DATE WRITTEN May 2005
1517 :
1518 : // PURPOSE OF THIS SUBROUTINE:
1519 : // This routine gets node data for a given Parent Component Type and Name Name.
1520 :
1521 : // METHODOLOGY EMPLOYED:
1522 : // Traverses CompSet structure.
1523 :
1524 : // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
1525 8714 : bool ErrInObject = false;
1526 :
1527 8714 : InletNodeName = std::string();
1528 8714 : InletNodeNum = 0;
1529 8714 : OutletNodeName = std::string();
1530 8714 : OutletNodeNum = 0;
1531 8714 : ErrInObject = false;
1532 :
1533 8714 : int Which = WhichParentSet(state, ComponentType, ComponentName);
1534 8714 : if (Which != 0) {
1535 7274 : InletNodeName = state.dataBranchNodeConnections->ParentNodeList(Which).InletNodeName;
1536 7274 : OutletNodeName = state.dataBranchNodeConnections->ParentNodeList(Which).OutletNodeName;
1537 : // Get Node Numbers
1538 7274 : InletNodeNum =
1539 7274 : Util::FindItemInList(InletNodeName, state.dataLoopNodes->NodeID({1, state.dataLoopNodes->NumOfNodes}), state.dataLoopNodes->NumOfNodes);
1540 7274 : OutletNodeNum =
1541 7274 : Util::FindItemInList(OutletNodeName, state.dataLoopNodes->NodeID({1, state.dataLoopNodes->NumOfNodes}), state.dataLoopNodes->NumOfNodes);
1542 1440 : } else if (IsParentObjectCompSet(state, ComponentType, ComponentName)) {
1543 1440 : Which = WhichCompSet(state, ComponentType, ComponentName);
1544 1440 : if (Which != 0) {
1545 1440 : InletNodeName = state.dataBranchNodeConnections->CompSets(Which).InletNodeName;
1546 1440 : OutletNodeName = state.dataBranchNodeConnections->CompSets(Which).OutletNodeName;
1547 1440 : InletNodeNum = Util::FindItemInList(
1548 2880 : InletNodeName, state.dataLoopNodes->NodeID({1, state.dataLoopNodes->NumOfNodes}), state.dataLoopNodes->NumOfNodes);
1549 1440 : OutletNodeNum = Util::FindItemInList(
1550 2880 : OutletNodeName, state.dataLoopNodes->NodeID({1, state.dataLoopNodes->NumOfNodes}), state.dataLoopNodes->NumOfNodes);
1551 : } else {
1552 0 : ErrInObject = true;
1553 0 : ShowWarningError(state,
1554 0 : format("GetParentData: Component Type={}, Component Name={} not found.",
1555 0 : ConnectionObjectTypeNames[static_cast<int>(ComponentType)],
1556 : ComponentName));
1557 : }
1558 : } else {
1559 0 : ErrInObject = true;
1560 0 : ShowWarningError(state,
1561 0 : format("GetParentData: Component Type={}, Component Name={} not found.",
1562 0 : ConnectionObjectTypeNames[static_cast<int>(ComponentType)],
1563 : ComponentName));
1564 : }
1565 :
1566 8714 : if (ErrInObject) {
1567 0 : ErrorsFound = true;
1568 : }
1569 8714 : }
1570 :
1571 37553 : bool IsParentObjectCompSet(EnergyPlusData &state, DataLoopNode::ConnectionObjectType const ComponentType, std::string const &ComponentName)
1572 : {
1573 :
1574 : // FUNCTION INFORMATION:
1575 : // AUTHOR Linda Lawrie
1576 : // DATE WRITTEN May 2005
1577 :
1578 : // PURPOSE OF THIS FUNCTION:
1579 : // This routine determines if a component name is a parent node.
1580 :
1581 : // METHODOLOGY EMPLOYED:
1582 : // Traverses CompSet structure.
1583 :
1584 : // Return value
1585 37553 : bool IsParent = false; // True if this combination is a parent
1586 :
1587 6728016 : for (int Loop = 1; Loop <= state.dataBranchNodeConnections->NumCompSets; ++Loop) {
1588 6890632 : if (state.dataBranchNodeConnections->CompSets(Loop).ParentObjectType == ComponentType &&
1589 186173 : state.dataBranchNodeConnections->CompSets(Loop).ParentCName == ComponentName) {
1590 13996 : IsParent = true;
1591 13996 : break;
1592 : }
1593 : }
1594 :
1595 37553 : return IsParent;
1596 : }
1597 :
1598 1440 : int WhichCompSet(EnergyPlusData &state, DataLoopNode::ConnectionObjectType const ComponentType, std::string const &ComponentName)
1599 : {
1600 :
1601 : // FUNCTION INFORMATION:
1602 : // AUTHOR Linda Lawrie
1603 : // DATE WRITTEN May 2005
1604 :
1605 : // PURPOSE OF THIS FUNCTION:
1606 : // This routine determines which comp set (number) for a given component name
1607 : // and type.
1608 :
1609 : // METHODOLOGY EMPLOYED:
1610 : // Traverses CompSet structure.
1611 :
1612 : // Return value
1613 1440 : int WhichOne = 0;
1614 :
1615 23999 : for (int Loop = 1; Loop <= state.dataBranchNodeConnections->NumCompSets; ++Loop) {
1616 30624 : if (state.dataBranchNodeConnections->CompSets(Loop).ComponentObjectType == ComponentType &&
1617 6625 : state.dataBranchNodeConnections->CompSets(Loop).CName == ComponentName) {
1618 1440 : WhichOne = Loop;
1619 1440 : break;
1620 : }
1621 : }
1622 :
1623 1440 : return WhichOne;
1624 : }
1625 :
1626 17464 : int GetNumChildren(EnergyPlusData &state, DataLoopNode::ConnectionObjectType const ComponentType, std::string const &ComponentName)
1627 : {
1628 :
1629 : // FUNCTION INFORMATION:
1630 : // AUTHOR Linda Lawrie
1631 : // DATE WRITTEN May 2005
1632 : // MODIFIED na
1633 : // RE-ENGINEERED na
1634 :
1635 : // PURPOSE OF THIS FUNCTION:
1636 : // This routine counts the number of children for a parent Component Set.
1637 :
1638 : // METHODOLOGY EMPLOYED:
1639 : // Traverses CompSet structure.
1640 :
1641 : // Return value
1642 : int NumChildren;
1643 :
1644 17464 : NumChildren = 0;
1645 17464 : if (IsParentObject(state, ComponentType, ComponentName)) {
1646 3428156 : for (int Loop = 1; Loop <= state.dataBranchNodeConnections->NumCompSets; ++Loop) {
1647 4127548 : if (state.dataBranchNodeConnections->CompSets(Loop).ParentObjectType == ComponentType &&
1648 716820 : state.dataBranchNodeConnections->CompSets(Loop).ParentCName == ComponentName) {
1649 25012 : ++NumChildren;
1650 : }
1651 : }
1652 : }
1653 :
1654 17464 : return NumChildren;
1655 : }
1656 :
1657 4794 : void GetComponentData(EnergyPlusData &state,
1658 : DataLoopNode::ConnectionObjectType const ComponentType,
1659 : std::string const &ComponentName,
1660 : bool &IsParent, // true or false
1661 : int &NumInlets,
1662 : Array1D_string &InletNodeNames,
1663 : Array1D_int &InletNodeNums,
1664 : Array1D<NodeInputManager::CompFluidStream> &InletFluidStreams,
1665 : int &NumOutlets,
1666 : Array1D_string &OutletNodeNames,
1667 : Array1D_int &OutletNodeNums,
1668 : Array1D<NodeInputManager::CompFluidStream> &OutletFluidStreams)
1669 : {
1670 :
1671 : // SUBROUTINE INFORMATION:
1672 : // AUTHOR Linda Lawrie
1673 : // DATE WRITTEN May 2005
1674 :
1675 : // PURPOSE OF THIS SUBROUTINE:
1676 : // This routine gets data for a given Component Type and Name Name.
1677 :
1678 : // METHODOLOGY EMPLOYED:
1679 : // Traverses CompSet structure.
1680 :
1681 4794 : if (allocated(InletNodeNames)) {
1682 16 : InletNodeNames.deallocate();
1683 : }
1684 4794 : if (allocated(InletNodeNums)) {
1685 16 : InletNodeNums.deallocate();
1686 : }
1687 4794 : if (allocated(InletFluidStreams)) {
1688 3567 : InletFluidStreams.deallocate();
1689 : }
1690 4794 : if (allocated(OutletNodeNames)) {
1691 16 : OutletNodeNames.deallocate();
1692 : }
1693 4794 : if (allocated(OutletNodeNums)) {
1694 16 : OutletNodeNums.deallocate();
1695 : }
1696 4794 : if (allocated(OutletFluidStreams)) {
1697 3567 : OutletFluidStreams.deallocate();
1698 : }
1699 :
1700 4794 : NumInlets = 0;
1701 4794 : NumOutlets = 0;
1702 :
1703 4794 : IsParent = false;
1704 6059675 : for (int Which = 1; Which <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Which) {
1705 6258078 : if (state.dataBranchNodeConnections->NodeConnections(Which).ObjectType != ComponentType ||
1706 203197 : state.dataBranchNodeConnections->NodeConnections(Which).ObjectName != ComponentName) {
1707 6048543 : continue;
1708 : }
1709 6338 : if (state.dataBranchNodeConnections->NodeConnections(Which).ObjectIsParent) {
1710 5408 : IsParent = true;
1711 : }
1712 6338 : if (state.dataBranchNodeConnections->NodeConnections(Which).ConnectionType == DataLoopNode::ConnectionType::Inlet) {
1713 1359 : ++NumInlets;
1714 4979 : } else if (state.dataBranchNodeConnections->NodeConnections(Which).ConnectionType == DataLoopNode::ConnectionType::Outlet) {
1715 4787 : ++NumOutlets;
1716 : }
1717 : }
1718 :
1719 4794 : InletNodeNames.allocate(NumInlets);
1720 4794 : InletNodeNums.allocate(NumInlets);
1721 4794 : InletFluidStreams.allocate(NumInlets);
1722 4794 : OutletNodeNames.allocate(NumOutlets);
1723 4794 : OutletNodeNums.allocate(NumOutlets);
1724 4794 : OutletFluidStreams.allocate(NumOutlets);
1725 :
1726 4794 : InletNodeNames = std::string();
1727 4794 : InletNodeNums = 0;
1728 4794 : InletFluidStreams = NodeInputManager::CompFluidStream::Invalid;
1729 4794 : OutletNodeNames = std::string();
1730 4794 : OutletNodeNums = 0;
1731 4794 : OutletFluidStreams = NodeInputManager::CompFluidStream::Invalid;
1732 4794 : NumInlets = 0;
1733 4794 : NumOutlets = 0;
1734 :
1735 6059675 : for (int Which = 1; Which <= state.dataBranchNodeConnections->NumOfNodeConnections; ++Which) {
1736 6258078 : if (state.dataBranchNodeConnections->NodeConnections(Which).ObjectType != ComponentType ||
1737 203197 : state.dataBranchNodeConnections->NodeConnections(Which).ObjectName != ComponentName) {
1738 6048543 : continue;
1739 : }
1740 6338 : if (state.dataBranchNodeConnections->NodeConnections(Which).ConnectionType == DataLoopNode::ConnectionType::Inlet) {
1741 1359 : ++NumInlets;
1742 1359 : InletNodeNames(NumInlets) = state.dataBranchNodeConnections->NodeConnections(Which).NodeName;
1743 1359 : InletNodeNums(NumInlets) = state.dataBranchNodeConnections->NodeConnections(Which).NodeNumber;
1744 1359 : InletFluidStreams(NumInlets) = state.dataBranchNodeConnections->NodeConnections(Which).FluidStream;
1745 4979 : } else if (state.dataBranchNodeConnections->NodeConnections(Which).ConnectionType == DataLoopNode::ConnectionType::Outlet) {
1746 4787 : ++NumOutlets;
1747 4787 : OutletNodeNames(NumOutlets) = state.dataBranchNodeConnections->NodeConnections(Which).NodeName;
1748 4787 : OutletNodeNums(NumOutlets) = state.dataBranchNodeConnections->NodeConnections(Which).NodeNumber;
1749 4787 : OutletFluidStreams(NumOutlets) = state.dataBranchNodeConnections->NodeConnections(Which).FluidStream;
1750 : }
1751 : }
1752 4794 : }
1753 :
1754 8714 : void GetChildrenData(EnergyPlusData &state,
1755 : DataLoopNode::ConnectionObjectType const ComponentType,
1756 : std::string const &ComponentName,
1757 : int &NumChildren,
1758 : EPVector<DataLoopNode::ConnectionObjectType> &ChildrenCType,
1759 : Array1D_string &ChildrenCName,
1760 : Array1D_string &InletNodeName,
1761 : Array1D_int &InletNodeNum,
1762 : Array1D_string &OutletNodeName,
1763 : Array1D_int &OutletNodeNum,
1764 : bool &ErrorsFound)
1765 : {
1766 :
1767 : // SUBROUTINE INFORMATION:
1768 : // AUTHOR Linda Lawrie
1769 : // DATE WRITTEN May 2005
1770 :
1771 : // PURPOSE OF THIS SUBROUTINE:
1772 : // This routine gets children data for given parent node.
1773 :
1774 : // METHODOLOGY EMPLOYED:
1775 : // Traverses CompSet structure.
1776 :
1777 : // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
1778 8714 : EPVector<DataLoopNode::ConnectionObjectType> ChildCType;
1779 8714 : Array1D_string ChildCName;
1780 8714 : Array1D_string ChildInNodeName;
1781 8714 : Array1D_string ChildOutNodeName;
1782 8714 : Array1D_int ChildInNodeNum;
1783 8714 : Array1D_int ChildOutNodeNum;
1784 8714 : Array1D_bool ChildMatched;
1785 :
1786 : bool ErrInObject;
1787 :
1788 8714 : std::fill(ChildrenCType.begin(), ChildrenCType.end(), DataLoopNode::ConnectionObjectType::Invalid);
1789 8714 : ChildrenCName = std::string();
1790 8714 : InletNodeName = std::string();
1791 8714 : InletNodeNum = 0;
1792 8714 : OutletNodeName = std::string();
1793 8714 : OutletNodeNum = 0;
1794 8714 : ErrInObject = false;
1795 :
1796 8714 : if (!IsParentObject(state, ComponentType, ComponentName)) {
1797 0 : ShowWarningError(state,
1798 0 : format("GetChildrenData: Requested Children Data for non Parent Node={}:{}.",
1799 0 : ConnectionObjectTypeNames[static_cast<int>(ComponentType)],
1800 : ComponentName));
1801 0 : ErrorsFound = true;
1802 :
1803 8714 : } else if ((NumChildren = GetNumChildren(state, ComponentType, ComponentName)) == 0) {
1804 0 : ShowWarningError(state,
1805 0 : format("GetChildrenData: Parent Node has no children, node={}:{}.",
1806 0 : ConnectionObjectTypeNames[static_cast<int>(ComponentType)],
1807 : ComponentName));
1808 :
1809 : } else {
1810 : int ParentInletNodeNum;
1811 : int ParentOutletNodeNum;
1812 8714 : std::string ParentInletNodeName;
1813 8714 : std::string ParentOutletNodeName;
1814 8714 : GetParentData(
1815 : state, ComponentType, ComponentName, ParentInletNodeName, ParentInletNodeNum, ParentOutletNodeName, ParentOutletNodeNum, ErrInObject);
1816 8714 : ChildCType.allocate(NumChildren);
1817 8714 : ChildCName.allocate(NumChildren);
1818 8714 : ChildInNodeName.allocate(NumChildren);
1819 8714 : ChildOutNodeName.allocate(NumChildren);
1820 8714 : ChildInNodeNum.allocate(NumChildren);
1821 8714 : ChildOutNodeNum.allocate(NumChildren);
1822 8714 : ChildMatched.allocate(NumChildren);
1823 :
1824 8714 : std::fill(ChildCType.begin(), ChildCType.end(), DataLoopNode::ConnectionObjectType::Invalid);
1825 8714 : ChildCName = std::string();
1826 8714 : ChildInNodeName = std::string();
1827 8714 : ChildOutNodeName = std::string();
1828 8714 : ChildInNodeNum = 0;
1829 8714 : ChildOutNodeNum = 0;
1830 8714 : ChildMatched = false;
1831 :
1832 8714 : int CountNum = 0;
1833 1714078 : for (int Loop = 1; Loop <= state.dataBranchNodeConnections->NumCompSets; ++Loop) {
1834 1705364 : auto const &compSet = state.dataBranchNodeConnections->CompSets(Loop);
1835 1705364 : if (compSet.ParentObjectType == ComponentType && compSet.ParentCName == ComponentName) {
1836 12506 : ++CountNum;
1837 12506 : ChildCType(CountNum) = compSet.ComponentObjectType;
1838 12506 : ChildCName(CountNum) = compSet.CName;
1839 12506 : ChildInNodeName(CountNum) = compSet.InletNodeName;
1840 12506 : ChildOutNodeName(CountNum) = compSet.OutletNodeName;
1841 : // Get Node Numbers
1842 12506 : ChildInNodeNum(CountNum) = Util::FindItemInList(ChildInNodeName(CountNum), state.dataLoopNodes->NodeID);
1843 12506 : ChildOutNodeNum(CountNum) = Util::FindItemInList(ChildOutNodeName(CountNum), state.dataLoopNodes->NodeID);
1844 : }
1845 : }
1846 :
1847 8714 : if (CountNum != NumChildren) {
1848 0 : ShowSevereError(state, "GetChildrenData: Counted nodes not equal to GetNumChildren count");
1849 0 : ErrorsFound = true;
1850 :
1851 : } else {
1852 : // Children arrays built. Now "sort" for flow connection order(?)
1853 : // FindIntInList is 0-based and FindItemInList is 1-based .. great!
1854 8714 : int ParentInletNodeIndex = 0;
1855 17704 : for (int Loop = 1; Loop <= NumChildren; ++Loop) {
1856 10576 : if (ChildInNodeNum(Loop) == ParentInletNodeNum) {
1857 1586 : ParentInletNodeIndex = Loop;
1858 1586 : break;
1859 : }
1860 : }
1861 :
1862 8714 : int ParentOutletNodeIndex = 0;
1863 11461 : for (int Loop = 1; Loop <= NumChildren; ++Loop) {
1864 11436 : if (ChildOutNodeNum(Loop) == ParentOutletNodeNum) {
1865 8689 : ParentOutletNodeIndex = Loop;
1866 8689 : break;
1867 : }
1868 : }
1869 :
1870 : // Parent inlet node matches one of the inlet-nodes of the sub-components
1871 8714 : if (ParentInletNodeIndex > 0) {
1872 1586 : int MatchInNodeNum = ParentInletNodeNum;
1873 1586 : CountNum = 0;
1874 :
1875 5405 : while (CountNum < NumChildren) {
1876 3847 : int MatchInNodeIndex = 0;
1877 8302 : for (int Loop = 1; Loop <= NumChildren; ++Loop) {
1878 8274 : if (ChildInNodeNum(Loop) == MatchInNodeNum && !ChildMatched(Loop)) {
1879 3819 : MatchInNodeIndex = Loop;
1880 3819 : break;
1881 : }
1882 : }
1883 :
1884 3847 : if (MatchInNodeIndex == 0) { // The chain is broken
1885 28 : break;
1886 : }
1887 :
1888 3819 : ++CountNum;
1889 3819 : ChildrenCType(CountNum) = ChildCType(MatchInNodeIndex);
1890 3819 : ChildrenCName(CountNum) = ChildCName(MatchInNodeIndex);
1891 3819 : InletNodeName(CountNum) = ChildInNodeName(MatchInNodeIndex);
1892 3819 : InletNodeNum(CountNum) = ChildInNodeNum(MatchInNodeIndex);
1893 3819 : OutletNodeName(CountNum) = ChildOutNodeName(MatchInNodeIndex);
1894 3819 : OutletNodeNum(CountNum) = ChildOutNodeNum(MatchInNodeIndex);
1895 3819 : ChildMatched(MatchInNodeIndex) = true;
1896 3819 : MatchInNodeNum = ChildOutNodeNum(MatchInNodeIndex);
1897 : }
1898 :
1899 5453 : for (int Loop = 1; Loop <= NumChildren; ++Loop) {
1900 3867 : if (ChildMatched(Loop)) {
1901 3819 : continue;
1902 : }
1903 48 : ++CountNum;
1904 48 : ChildrenCType(CountNum) = ChildCType(Loop);
1905 48 : ChildrenCName(CountNum) = ChildCName(Loop);
1906 48 : InletNodeName(CountNum) = ChildInNodeName(Loop);
1907 48 : InletNodeNum(CountNum) = ChildInNodeNum(Loop);
1908 48 : OutletNodeName(CountNum) = ChildOutNodeName(Loop);
1909 48 : OutletNodeNum(CountNum) = ChildOutNodeNum(Loop);
1910 : }
1911 :
1912 : // Parent outlet node matches one of the outlet-nodes of the sub-components
1913 7128 : } else if (ParentOutletNodeIndex > 0) {
1914 7107 : int MatchOutNodeNum = ParentOutletNodeNum;
1915 7107 : CountNum = NumChildren + 1;
1916 :
1917 15535 : while (CountNum > 1) {
1918 8575 : int MatchOutNodeIndex = 0;
1919 11444 : for (int Loop = 1; Loop <= NumChildren; ++Loop) {
1920 11297 : if (ChildOutNodeNum(Loop) == MatchOutNodeNum && !ChildMatched(Loop)) {
1921 8428 : MatchOutNodeIndex = Loop;
1922 8428 : break;
1923 : }
1924 : }
1925 :
1926 8575 : if (MatchOutNodeIndex == 0) { // The chain is broken
1927 147 : break;
1928 : }
1929 :
1930 8428 : --CountNum;
1931 8428 : ChildrenCType(CountNum) = ChildCType(MatchOutNodeIndex);
1932 8428 : ChildrenCName(CountNum) = ChildCName(MatchOutNodeIndex);
1933 8428 : InletNodeName(CountNum) = ChildInNodeName(MatchOutNodeIndex);
1934 8428 : InletNodeNum(CountNum) = ChildInNodeNum(MatchOutNodeIndex);
1935 8428 : OutletNodeName(CountNum) = ChildOutNodeName(MatchOutNodeIndex);
1936 8428 : OutletNodeNum(CountNum) = ChildOutNodeNum(MatchOutNodeIndex);
1937 8428 : ChildMatched(MatchOutNodeIndex) = true;
1938 8428 : MatchOutNodeNum = ChildInNodeNum(MatchOutNodeIndex);
1939 : }
1940 :
1941 7107 : CountNum = 0;
1942 15682 : for (int Loop = 1; Loop <= NumChildren; ++Loop) {
1943 8575 : if (ChildMatched(Loop)) {
1944 8428 : continue;
1945 : }
1946 147 : ++CountNum;
1947 147 : ChildrenCType(CountNum) = ChildCType(Loop);
1948 147 : ChildrenCName(CountNum) = ChildCName(Loop);
1949 147 : InletNodeName(CountNum) = ChildInNodeName(Loop);
1950 147 : InletNodeNum(CountNum) = ChildInNodeNum(Loop);
1951 147 : OutletNodeName(CountNum) = ChildOutNodeName(Loop);
1952 147 : OutletNodeNum(CountNum) = ChildOutNodeNum(Loop);
1953 : }
1954 : } else {
1955 : // No sub-component is connected to either the parent
1956 : // component's inlet- or outlet- nodes? Just copy the
1957 : // sub-components in the order in which they appear in
1958 : // the CompSets
1959 :
1960 85 : for (int Loop = 1; Loop <= NumChildren; ++Loop) {
1961 64 : if (ChildMatched(Loop)) {
1962 0 : continue;
1963 : }
1964 64 : ChildrenCType(Loop) = ChildCType(Loop);
1965 64 : ChildrenCName(Loop) = ChildCName(Loop);
1966 64 : InletNodeName(Loop) = ChildInNodeName(Loop);
1967 64 : InletNodeNum(Loop) = ChildInNodeNum(Loop);
1968 64 : OutletNodeName(Loop) = ChildOutNodeName(Loop);
1969 64 : OutletNodeNum(Loop) = ChildOutNodeNum(Loop);
1970 : }
1971 : }
1972 : }
1973 :
1974 8714 : ChildCType.deallocate();
1975 8714 : ChildCName.deallocate();
1976 8714 : ChildInNodeName.deallocate();
1977 8714 : ChildOutNodeName.deallocate();
1978 8714 : ChildInNodeNum.deallocate();
1979 8714 : ChildOutNodeNum.deallocate();
1980 8714 : ChildMatched.deallocate();
1981 8714 : }
1982 :
1983 8714 : if (ErrInObject) {
1984 0 : ErrorsFound = true;
1985 : }
1986 8714 : }
1987 :
1988 38243 : void SetUpCompSets(EnergyPlusData &state,
1989 : std::string_view ParentType, // Parent Object Type
1990 : std::string_view ParentName, // Parent Object Name
1991 : std::string_view CompType, // Component Type
1992 : std::string_view CompName, // Component Name
1993 : std::string_view InletNode, // Inlet Node Name
1994 : std::string_view OutletNode, // Outlet Node Name
1995 : std::string_view const Description // Description
1996 : )
1997 : {
1998 :
1999 : // SUBROUTINE INFORMATION:
2000 : // AUTHOR Linda Lawrie
2001 : // DATE WRITTEN November 2001
2002 :
2003 : // PURPOSE OF THIS SUBROUTINE:
2004 : // This subroutine sets up "Component Sets" as input in the branch
2005 : // lists. These can be used later to verify that the proper names and
2006 : // inlet/outlet nodes have been input. This routine assumes that identical
2007 : // "CompSets" cannot be used in multiple places and issues a warning if they are.
2008 :
2009 38243 : std::string ParentTypeUC = Util::makeUPPER(ParentType);
2010 38243 : std::string CompTypeUC = Util::makeUPPER(CompType);
2011 : // TODO: Refactor this away by passing in enums
2012 : DataLoopNode::ConnectionObjectType ParentTypeEnum =
2013 38243 : static_cast<DataLoopNode::ConnectionObjectType>(getEnumValue(ConnectionObjectTypeNamesUC, ParentTypeUC));
2014 38243 : assert(ParentTypeEnum != DataLoopNode::ConnectionObjectType::Invalid);
2015 :
2016 : DataLoopNode::ConnectionObjectType ComponentTypeEnum =
2017 38243 : static_cast<DataLoopNode::ConnectionObjectType>(getEnumValue(ConnectionObjectTypeNamesUC, CompTypeUC));
2018 38243 : assert(ComponentTypeEnum != DataLoopNode::ConnectionObjectType::Invalid);
2019 :
2020 38243 : int Found = 0;
2021 :
2022 : // See if Component-Nodes set is already there - should be unique
2023 : // Try to fill in blanks (passed in as undefined
2024 4729755 : for (int Count = 1; Count <= state.dataBranchNodeConnections->NumCompSets; ++Count) {
2025 4699205 : if (CompName != state.dataBranchNodeConnections->CompSets(Count).CName) {
2026 4683581 : continue;
2027 : }
2028 15624 : if (ComponentTypeEnum != DataLoopNode::ConnectionObjectType::Undefined) {
2029 15164 : if (ComponentTypeEnum != state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType) {
2030 29 : continue;
2031 : }
2032 : }
2033 : // Component name matches, component type matches or is undefined
2034 15595 : if (InletNode != undefined) {
2035 13583 : if (state.dataBranchNodeConnections->CompSets(Count).InletNodeName != undefined) {
2036 13582 : if (InletNode != state.dataBranchNodeConnections->CompSets(Count).InletNodeName) {
2037 7291 : continue;
2038 : }
2039 : } else {
2040 1 : state.dataBranchNodeConnections->CompSets(Count).InletNodeName = InletNode;
2041 : }
2042 : }
2043 8304 : if (OutletNode != undefined) {
2044 6745 : if (state.dataBranchNodeConnections->CompSets(Count).OutletNodeName != undefined) {
2045 6744 : if (OutletNode != state.dataBranchNodeConnections->CompSets(Count).OutletNodeName) {
2046 167 : continue;
2047 : }
2048 : } else {
2049 1 : state.dataBranchNodeConnections->CompSets(Count).OutletNodeName = OutletNode;
2050 : }
2051 : }
2052 : // See if something undefined and set here
2053 15830 : if (state.dataBranchNodeConnections->CompSets(Count).ParentObjectType == DataLoopNode::ConnectionObjectType::Undefined &&
2054 7693 : state.dataBranchNodeConnections->CompSets(Count).ParentCName == undefined) {
2055 : // Assume this is a further definition for this compset
2056 7693 : state.dataBranchNodeConnections->CompSets(Count).ParentObjectType = ParentTypeEnum;
2057 7693 : state.dataBranchNodeConnections->CompSets(Count).ParentCName = ParentName;
2058 7693 : if (!Description.empty()) {
2059 45 : state.dataBranchNodeConnections->CompSets(Count).Description = Description;
2060 : }
2061 7693 : Found = Count;
2062 7693 : break;
2063 : }
2064 : }
2065 38243 : if (Found == 0) {
2066 3051363 : for (int Count = 1; Count <= state.dataBranchNodeConnections->NumCompSets; ++Count) {
2067 3020813 : Found = 0;
2068 : // Test if inlet node has been used before as an inlet node
2069 : // If the matching node name does not belong to the parent object, then error
2070 : // For example a fan may share the same inlet node as the furnace object which is its parent
2071 3020813 : if (InletNode != state.dataBranchNodeConnections->CompSets(Count).InletNodeName) {
2072 2956074 : continue;
2073 : // If parent type is undefined then no error
2074 128687 : } else if ((ParentTypeEnum == DataLoopNode::ConnectionObjectType::Undefined) ||
2075 63948 : (state.dataBranchNodeConnections->CompSets(Count).ParentObjectType == DataLoopNode::ConnectionObjectType::Undefined)) {
2076 : // If node name is undefined then no error
2077 63940 : } else if (InletNode != undefined) {
2078 : // If the matching node name does not belong to the parent or child object, then error
2079 : // For example a fan may share the same inlet node as the furnace object which is its parent
2080 0 : if ((ParentTypeEnum == state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType) &&
2081 0 : (ParentName == state.dataBranchNodeConnections->CompSets(Count).CName)) {
2082 : // OK - The duplicate inlet node belongs to this component's parent
2083 0 : } else if ((ComponentTypeEnum == state.dataBranchNodeConnections->CompSets(Count).ParentObjectType) &&
2084 0 : (CompName == state.dataBranchNodeConnections->CompSets(Count).ParentCName)) {
2085 : // OK - The duplicate inlet node belongs to a child of this component
2086 : } else {
2087 : // Due to possibility of grandparents or more, if the matching node name
2088 : // belongs to a component that appears as a parent, then OK
2089 0 : int Found2 = 0;
2090 0 : for (int Count2 = 1; Count2 <= state.dataBranchNodeConnections->NumCompSets; ++Count2) {
2091 0 : if ((state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType ==
2092 0 : state.dataBranchNodeConnections->CompSets(Count2).ParentObjectType) &&
2093 0 : (state.dataBranchNodeConnections->CompSets(Count).CName ==
2094 0 : state.dataBranchNodeConnections->CompSets(Count2).ParentCName)) {
2095 0 : Found2 = 1;
2096 : }
2097 0 : if ((ComponentTypeEnum == state.dataBranchNodeConnections->CompSets(Count2).ParentObjectType) &&
2098 0 : (CompName == state.dataBranchNodeConnections->CompSets(Count2).ParentCName)) {
2099 0 : Found2 = 1;
2100 : }
2101 : }
2102 0 : if (Found2 == 0) {
2103 0 : ShowWarningError(state, format("Node used as an inlet more than once: {}", InletNode));
2104 0 : ShowContinueError(
2105 : state,
2106 0 : format(" Used by: {}, name={}",
2107 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Count).ParentObjectType)],
2108 0 : state.dataBranchNodeConnections->CompSets(Count).ParentCName));
2109 0 : ShowContinueError(
2110 : state,
2111 0 : format(" as inlet for: {}, name={}",
2112 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType)],
2113 0 : state.dataBranchNodeConnections->CompSets(Count).CName));
2114 0 : ShowContinueError(state, format("{}{}{}", " and by : ", ParentTypeUC + ", name=", ParentName));
2115 0 : ShowContinueError(state, format("{}{}{}", " as inlet for: ", CompTypeUC + ", name=", CompName));
2116 : }
2117 : }
2118 : }
2119 : // Test if outlet node has been used before as an outlet node
2120 : // If the matching node name does not belong to the parent or child object, then error
2121 : // For example a fan may share the same outlet node as the furnace object which is its parent
2122 64739 : if (OutletNode != state.dataBranchNodeConnections->CompSets(Count).OutletNodeName) {
2123 59032 : continue;
2124 : // If parent type is undefined then no error
2125 11113 : } else if ((ParentTypeEnum == DataLoopNode::ConnectionObjectType::Undefined) ||
2126 5406 : (state.dataBranchNodeConnections->CompSets(Count).ParentObjectType == DataLoopNode::ConnectionObjectType::Undefined)) {
2127 : // If node name is undefined then no error
2128 5403 : } else if (OutletNode != undefined) {
2129 29 : if ((ParentTypeEnum == state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType) &&
2130 0 : (ParentName == state.dataBranchNodeConnections->CompSets(Count).CName)) {
2131 : // OK - The duplicate outlet node belongs to this component's parent
2132 29 : } else if ((ComponentTypeEnum == state.dataBranchNodeConnections->CompSets(Count).ParentObjectType) &&
2133 0 : (CompName == state.dataBranchNodeConnections->CompSets(Count).ParentCName)) {
2134 : // OK - The duplicate outlet node belongs to a child of this component
2135 : } else {
2136 : // Due to possibility of grandparents or more, if the matching node name
2137 : // belongs to a component that appears as a parent, then OK
2138 29 : int Found2 = 0;
2139 1160 : for (int Count2 = 1; Count2 <= state.dataBranchNodeConnections->NumCompSets; ++Count2) {
2140 1131 : if ((state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType ==
2141 1131 : state.dataBranchNodeConnections->CompSets(Count2).ParentObjectType) &&
2142 0 : (state.dataBranchNodeConnections->CompSets(Count).CName ==
2143 0 : state.dataBranchNodeConnections->CompSets(Count2).ParentCName)) {
2144 0 : Found2 = 1;
2145 : }
2146 1131 : if ((ComponentTypeEnum == state.dataBranchNodeConnections->CompSets(Count2).ParentObjectType) &&
2147 0 : (CompName == state.dataBranchNodeConnections->CompSets(Count2).ParentCName)) {
2148 0 : Found2 = 1;
2149 : }
2150 : }
2151 : // This rule is violated by dual duct units, so let it pass
2152 29 : if (Found2 == 0) {
2153 : std::string_view const CType =
2154 29 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType)];
2155 29 : if ((!has_prefixi(CType, "AirTerminal:DualDuct:")) && (!has_prefixi(CompTypeUC, "AirTerminal:DualDuct:"))) {
2156 0 : ShowWarningError(state, format("Node used as an outlet more than once: {}", OutletNode));
2157 0 : ShowContinueError(
2158 : state,
2159 0 : format(" Used by: {}, name={}",
2160 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Count).ParentObjectType)],
2161 0 : state.dataBranchNodeConnections->CompSets(Count).ParentCName));
2162 0 : ShowContinueError(
2163 : state,
2164 0 : format(
2165 : " as outlet for: {}, name={}",
2166 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType)],
2167 0 : state.dataBranchNodeConnections->CompSets(Count).CName));
2168 0 : ShowContinueError(state, format("{}{}{}", " and by : ", ParentTypeUC + ", name=", ParentName));
2169 0 : ShowContinueError(state, format("{}{}{}", " as outlet for: ", CompTypeUC + ", name=", CompName));
2170 : }
2171 : }
2172 : }
2173 : }
2174 5707 : if (ComponentTypeEnum != state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType &&
2175 : ComponentTypeEnum != DataLoopNode::ConnectionObjectType::Undefined) {
2176 497 : continue;
2177 : }
2178 5210 : if (CompName != state.dataBranchNodeConnections->CompSets(Count).CName) {
2179 5210 : continue;
2180 : }
2181 0 : Found = Count;
2182 0 : break;
2183 : }
2184 : }
2185 38243 : if (Found == 0) {
2186 30550 : state.dataBranchNodeConnections->CompSets.resize(++state.dataBranchNodeConnections->NumCompSets);
2187 30550 : state.dataBranchNodeConnections->CompSets(state.dataBranchNodeConnections->NumCompSets).ParentObjectType = ParentTypeEnum;
2188 :
2189 30550 : state.dataBranchNodeConnections->CompSets(state.dataBranchNodeConnections->NumCompSets).ParentCName = ParentName;
2190 30550 : state.dataBranchNodeConnections->CompSets(state.dataBranchNodeConnections->NumCompSets).ComponentObjectType = ComponentTypeEnum;
2191 30550 : state.dataBranchNodeConnections->CompSets(state.dataBranchNodeConnections->NumCompSets).CName = CompName;
2192 30550 : state.dataBranchNodeConnections->CompSets(state.dataBranchNodeConnections->NumCompSets).InletNodeName =
2193 :
2194 61100 : Util::makeUPPER(InletNode); // TODO: Fix this....
2195 30550 : state.dataBranchNodeConnections->CompSets(state.dataBranchNodeConnections->NumCompSets).OutletNodeName =
2196 61100 : Util::makeUPPER(OutletNode); // TODO: Fix this....
2197 :
2198 30550 : if (!Description.empty()) {
2199 7735 : state.dataBranchNodeConnections->CompSets(state.dataBranchNodeConnections->NumCompSets).Description = Description;
2200 : } else {
2201 22815 : state.dataBranchNodeConnections->CompSets(state.dataBranchNodeConnections->NumCompSets).Description = undefined;
2202 : }
2203 : }
2204 38243 : }
2205 :
2206 639 : void TestInletOutletNodes(EnergyPlusData &state)
2207 : {
2208 :
2209 : // SUBROUTINE INFORMATION:
2210 : // AUTHOR Linda Lawrie
2211 : // DATE WRITTEN November 2001
2212 :
2213 : // PURPOSE OF THIS SUBROUTINE:
2214 : // This subroutine tests the branches to see if a duplicate inlet node
2215 : // exists under a different name in the sequence; likewise for outlet.
2216 :
2217 639 : Array1D_bool AlreadyNoted;
2218 :
2219 : // Test component sets created by branches
2220 639 : AlreadyNoted.dimension(state.dataBranchNodeConnections->NumCompSets, false);
2221 18510 : for (int Count = 1; Count <= state.dataBranchNodeConnections->NumCompSets; ++Count) {
2222 1500960 : for (int Other = 1; Other <= state.dataBranchNodeConnections->NumCompSets; ++Other) {
2223 1483089 : if (Count == Other) {
2224 17871 : continue;
2225 : }
2226 1465218 : if (state.dataBranchNodeConnections->CompSets(Count).InletNodeName != state.dataBranchNodeConnections->CompSets(Other).InletNodeName) {
2227 1465218 : continue;
2228 : }
2229 0 : if (AlreadyNoted(Count)) {
2230 0 : continue;
2231 : }
2232 : // All other values must match
2233 0 : if (state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType !=
2234 0 : state.dataBranchNodeConnections->CompSets(Other).ComponentObjectType ||
2235 0 : state.dataBranchNodeConnections->CompSets(Count).CName != state.dataBranchNodeConnections->CompSets(Other).CName ||
2236 0 : state.dataBranchNodeConnections->CompSets(Count).OutletNodeName != state.dataBranchNodeConnections->CompSets(Other).OutletNodeName) {
2237 0 : AlreadyNoted(Other) = true;
2238 0 : ShowWarningError(state,
2239 0 : format("Node used as an inlet more than once: {}", state.dataBranchNodeConnections->CompSets(Count).InletNodeName));
2240 0 : ShowContinueError(
2241 : state,
2242 0 : format(" Used by: {}, name={}",
2243 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Count).ParentObjectType)],
2244 0 : state.dataBranchNodeConnections->CompSets(Count).ParentCName));
2245 0 : ShowContinueError(
2246 : state,
2247 0 : format(" as inlet for: {}, name={}",
2248 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Other).ComponentObjectType)],
2249 0 : state.dataBranchNodeConnections->CompSets(Other).CName));
2250 0 : ShowContinueError(
2251 : state,
2252 0 : format(" and by: {}, name={}",
2253 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Other).ParentObjectType)],
2254 0 : state.dataBranchNodeConnections->CompSets(Other).ParentCName));
2255 0 : ShowContinueError(
2256 : state,
2257 0 : format(" as inlet for: {}, name={}",
2258 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType)],
2259 0 : state.dataBranchNodeConnections->CompSets(Count).CName));
2260 : }
2261 : }
2262 : }
2263 :
2264 639 : AlreadyNoted = false;
2265 18510 : for (int Count = 1; Count <= state.dataBranchNodeConnections->NumCompSets; ++Count) {
2266 1500960 : for (int Other = 1; Other <= state.dataBranchNodeConnections->NumCompSets; ++Other) {
2267 1483089 : if (Count == Other) {
2268 17871 : continue;
2269 : }
2270 1465218 : if (state.dataBranchNodeConnections->CompSets(Count).OutletNodeName != state.dataBranchNodeConnections->CompSets(Other).OutletNodeName) {
2271 1465218 : continue;
2272 : }
2273 0 : if (AlreadyNoted(Count)) {
2274 0 : continue;
2275 : }
2276 : // All other values must match
2277 0 : if (state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType !=
2278 0 : state.dataBranchNodeConnections->CompSets(Other).ComponentObjectType ||
2279 0 : state.dataBranchNodeConnections->CompSets(Count).CName != state.dataBranchNodeConnections->CompSets(Other).CName ||
2280 0 : state.dataBranchNodeConnections->CompSets(Count).InletNodeName != state.dataBranchNodeConnections->CompSets(Other).InletNodeName) {
2281 0 : AlreadyNoted(Other) = true;
2282 0 : ShowWarningError(
2283 0 : state, format("Node used as an outlet more than once: {}", state.dataBranchNodeConnections->CompSets(Count).OutletNodeName));
2284 0 : ShowContinueError(
2285 : state,
2286 0 : format(" Used by: {}, name={}",
2287 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Count).ParentObjectType)],
2288 0 : state.dataBranchNodeConnections->CompSets(Count).ParentCName));
2289 0 : ShowContinueError(
2290 : state,
2291 0 : format(" as outlet for: {}, name={}",
2292 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Other).ComponentObjectType)],
2293 0 : state.dataBranchNodeConnections->CompSets(Other).CName));
2294 0 : ShowContinueError(
2295 : state,
2296 0 : format(" and by: {}, name={}",
2297 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Other).ParentObjectType)],
2298 0 : state.dataBranchNodeConnections->CompSets(Other).ParentCName));
2299 0 : ShowContinueError(
2300 : state,
2301 0 : format(" as outlet for: {}, name={}",
2302 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType)],
2303 0 : state.dataBranchNodeConnections->CompSets(Count).CName));
2304 : }
2305 : }
2306 : }
2307 :
2308 639 : AlreadyNoted.deallocate();
2309 639 : }
2310 :
2311 30429 : void TestCompSet(EnergyPlusData &state,
2312 : std::string_view const CompType, // Component Type
2313 : std::string_view CompName, // Component Name
2314 : std::string const &InletNode, // Inlet Node Name
2315 : std::string const &OutletNode, // Outlet Node Name
2316 : std::string const &Description // Description of Node Pair (for warning message)
2317 : )
2318 : {
2319 :
2320 : // SUBROUTINE INFORMATION:
2321 : // AUTHOR Linda K. Lawrie
2322 : // DATE WRITTEN November 2001
2323 :
2324 : // PURPOSE OF THIS SUBROUTINE:
2325 : // Register a child component in the CompSets data structure.
2326 : // NOTE: This function was originally designed to test the stored "Component Sets" to
2327 : // see if there was one of this combination in there. Thus the name "TestCompSet".
2328 : // However, this was based on a false assumption that input would always be gotten
2329 : // first for the parent object, then for the child object. But this is often not the
2330 : // case. Ultimately, the name of this function should be changed or it should be merged
2331 : // into SetUpCompSets.
2332 : // Until then, this function does the following:
2333 : // a) Search CompSets for this combination of component type, component name,
2334 : // inlet node and outlet node. If component type/name match and the existing
2335 : // node names are UNDEFINED, this compset is assumed to be a match.
2336 : // b) If found, fill in any missing data such as node names or node description
2337 : // c) If not found, call SetUpCompSets (with parent type and name UNDEFINED)
2338 : // to add a new item in the CompSets array
2339 :
2340 30429 : std::string CompTypeUC = Util::makeUPPER(CompType);
2341 :
2342 : // TODO: Refactor this away by passing in enums
2343 : DataLoopNode::ConnectionObjectType ComponentTypeEnum =
2344 30429 : static_cast<DataLoopNode::ConnectionObjectType>(getEnumValue(ConnectionObjectTypeNamesUC, CompTypeUC));
2345 30429 : assert(ComponentTypeEnum != DataLoopNode::ConnectionObjectType::Invalid);
2346 :
2347 : // See if Already there
2348 30429 : int Found = 0;
2349 3048321 : for (int Count = 1; Count <= state.dataBranchNodeConnections->NumCompSets; ++Count) {
2350 5538006 : if ((ComponentTypeEnum != state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType) &&
2351 2497386 : (state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType != DataLoopNode::ConnectionObjectType::Undefined)) {
2352 2497386 : continue;
2353 : }
2354 543234 : if (CompName != state.dataBranchNodeConnections->CompSets(Count).CName) {
2355 515846 : continue;
2356 : }
2357 38026 : if ((InletNode != state.dataBranchNodeConnections->CompSets(Count).InletNodeName) &&
2358 38026 : (state.dataBranchNodeConnections->CompSets(Count).InletNodeName != undefined) && (InletNode != undefined)) {
2359 4660 : continue;
2360 : }
2361 24901 : if ((OutletNode != state.dataBranchNodeConnections->CompSets(Count).OutletNodeName) &&
2362 24901 : (state.dataBranchNodeConnections->CompSets(Count).OutletNodeName != undefined) && (OutletNode != undefined)) {
2363 0 : continue;
2364 : }
2365 :
2366 22728 : Found = Count;
2367 22728 : break;
2368 : }
2369 :
2370 30429 : if (Found == 0) {
2371 7701 : SetUpCompSets(state, undefined, undefined, CompType, CompName, InletNode, OutletNode, Description);
2372 : } else {
2373 : // Fill in node names and component type for previously undefined values:
2374 : // If the parent object did not specify a component type or inlet or outlet node, then that value
2375 : // is UNDEFINED in CompSets. When a component calls TestCompSet, the comp type and inlet and
2376 : // outlet nodes are known, so they can be filled in for future reference.
2377 22728 : if (state.dataBranchNodeConnections->CompSets(Found).ComponentObjectType == DataLoopNode::ConnectionObjectType::Undefined) {
2378 0 : state.dataBranchNodeConnections->CompSets(Found).ComponentObjectType = ComponentTypeEnum;
2379 : }
2380 22728 : if (state.dataBranchNodeConnections->CompSets(Found).InletNodeName == undefined) {
2381 4904 : state.dataBranchNodeConnections->CompSets(Found).InletNodeName = InletNode;
2382 : }
2383 22728 : if (state.dataBranchNodeConnections->CompSets(Found).OutletNodeName == undefined) {
2384 1099 : state.dataBranchNodeConnections->CompSets(Found).OutletNodeName = OutletNode;
2385 : }
2386 22728 : if (state.dataBranchNodeConnections->CompSets(Found).Description == undefined) {
2387 22705 : state.dataBranchNodeConnections->CompSets(Found).Description = Description;
2388 : }
2389 : }
2390 30429 : }
2391 :
2392 782 : void TestCompSetInletOutletNodes(EnergyPlusData &state, bool &ErrorsFound)
2393 : {
2394 :
2395 : // SUBROUTINE INFORMATION:
2396 : // AUTHOR Linda Lawrie
2397 : // DATE WRITTEN March 2008
2398 : // MODIFIED na
2399 : // RE-ENGINEERED na
2400 :
2401 : // PURPOSE OF THIS SUBROUTINE:
2402 : // This subroutine tests the comp sets to see if a duplicate comp name
2403 : // exists under a different set of inlet/outlet nodes.
2404 :
2405 : // SUBROUTINE LOCAL VARIABLE DECLARATIONS:
2406 782 : Array1D_bool AlreadyNoted;
2407 :
2408 : // Test component sets created by branches
2409 782 : AlreadyNoted.dimension(state.dataBranchNodeConnections->NumCompSets, false);
2410 29426 : for (int Count = 1; Count <= state.dataBranchNodeConnections->NumCompSets; ++Count) {
2411 5783036 : for (int Other = 1; Other <= state.dataBranchNodeConnections->NumCompSets; ++Other) {
2412 5754392 : if (Count == Other) {
2413 28644 : continue;
2414 : }
2415 5725748 : if (state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType ==
2416 : DataLoopNode::ConnectionObjectType ::SolarCollectorUnglazedTranspired) {
2417 558 : continue;
2418 : }
2419 5725190 : if (state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType !=
2420 6689742 : state.dataBranchNodeConnections->CompSets(Other).ComponentObjectType ||
2421 964552 : state.dataBranchNodeConnections->CompSets(Count).CName != state.dataBranchNodeConnections->CompSets(Other).CName) {
2422 5716670 : continue;
2423 : }
2424 8520 : if (state.dataBranchNodeConnections->CompSets(Count).Description != state.dataBranchNodeConnections->CompSets(Other).Description) {
2425 17040 : if (state.dataBranchNodeConnections->CompSets(Count).Description != undefined &&
2426 8520 : state.dataBranchNodeConnections->CompSets(Other).Description != undefined) {
2427 8520 : continue;
2428 : }
2429 : }
2430 0 : if (state.dataBranchNodeConnections->CompSets(Count).InletNodeName == state.dataBranchNodeConnections->CompSets(Other).InletNodeName) {
2431 0 : continue;
2432 : }
2433 0 : if (state.dataBranchNodeConnections->CompSets(Count).OutletNodeName == state.dataBranchNodeConnections->CompSets(Other).OutletNodeName) {
2434 0 : continue;
2435 : }
2436 0 : if (AlreadyNoted(Count)) {
2437 0 : continue;
2438 : }
2439 : // All other values must match
2440 0 : AlreadyNoted(Other) = true;
2441 0 : ShowSevereError(state, "Same component name and type has differing Node Names.");
2442 0 : ShowContinueError(
2443 : state,
2444 0 : format(" Component: {}, name={}",
2445 0 : ConnectionObjectTypeNames[static_cast<int>(state.dataBranchNodeConnections->CompSets(Count).ComponentObjectType)],
2446 0 : state.dataBranchNodeConnections->CompSets(Count).CName));
2447 0 : ShowContinueError(state,
2448 0 : format(" Nodes, inlet: {}, outlet: {}",
2449 0 : state.dataBranchNodeConnections->CompSets(Count).InletNodeName,
2450 0 : state.dataBranchNodeConnections->CompSets(Count).OutletNodeName));
2451 0 : ShowContinueError(state,
2452 0 : format(" & Nodes, inlet: {}, outlet: {}",
2453 0 : state.dataBranchNodeConnections->CompSets(Other).InletNodeName,
2454 0 : state.dataBranchNodeConnections->CompSets(Other).OutletNodeName));
2455 0 : ShowContinueError(state,
2456 0 : format(" Node Types: {} & {}",
2457 0 : state.dataBranchNodeConnections->CompSets(Count).Description,
2458 0 : state.dataBranchNodeConnections->CompSets(Other).Description));
2459 0 : ErrorsFound = true;
2460 : }
2461 : }
2462 :
2463 782 : AlreadyNoted.deallocate();
2464 782 : }
2465 :
2466 63 : void GetNodeConnectionType(EnergyPlusData &state, int const NodeNumber, EPVector<DataLoopNode::ConnectionType> &NodeConnectType, bool &errFlag)
2467 : {
2468 :
2469 : // FUNCTION INFORMATION:
2470 : // AUTHOR Lixing Gu
2471 : // DATE WRITTEN Jan 2007
2472 :
2473 : // PURPOSE OF THIS FUNCTION:
2474 : // This function provides a connection type with given node number
2475 :
2476 63 : Array1D_int ListArray;
2477 63 : Array1D_string ConnectionTypes(15);
2478 :
2479 1008 : for (int nodetype = 1; nodetype < static_cast<int>(ConnectionType::Num); ++nodetype) {
2480 945 : ConnectionTypes(nodetype) = ConnectionTypeNames[nodetype];
2481 : }
2482 :
2483 63 : if (allocated(NodeConnectType)) {
2484 42 : NodeConnectType.deallocate();
2485 : }
2486 :
2487 : int NumInList;
2488 126 : FindAllNodeNumbersInList(
2489 63 : NodeNumber, state.dataBranchNodeConnections->NodeConnections, state.dataBranchNodeConnections->NumOfNodeConnections, NumInList, ListArray);
2490 :
2491 63 : NodeConnectType.allocate(NumInList);
2492 :
2493 63 : if (NumInList > 0) {
2494 158 : for (int NodeConnectIndex = 1; NodeConnectIndex <= NumInList; ++NodeConnectIndex) {
2495 95 : NodeConnectType(NodeConnectIndex) = state.dataBranchNodeConnections->NodeConnections(ListArray(NodeConnectIndex)).ConnectionType;
2496 : }
2497 : } else {
2498 0 : if (NodeNumber > 0) {
2499 0 : ShowWarningError(state, format("Node not found = {}.", state.dataLoopNodes->NodeID(NodeNumber)));
2500 : } else {
2501 0 : ShowWarningError(state, "Invalid node number passed = 0.");
2502 : }
2503 0 : errFlag = true;
2504 : }
2505 63 : }
2506 :
2507 63 : void FindAllNodeNumbersInList(int const WhichNumber,
2508 : EPVector<DataBranchNodeConnections::NodeConnectionDef> const &NodeConnections,
2509 : int const NumItems,
2510 : int &CountOfItems, // Number of items found
2511 : Array1D_int &AllNumbersInList // Index array to all numbers found
2512 : )
2513 : {
2514 :
2515 : // FUNCTION INFORMATION:
2516 : // AUTHOR R. Raustad
2517 : // DATE WRITTEN January 2007
2518 :
2519 : // PURPOSE OF THIS FUNCTION:
2520 : // This function looks up a number(integer) in a similar list of
2521 : // items and returns the index of the item in the list, if
2522 : // found.
2523 :
2524 63 : CountOfItems = 0;
2525 :
2526 63 : if (allocated(AllNumbersInList)) {
2527 0 : AllNumbersInList.deallocate();
2528 : }
2529 :
2530 4179 : for (int Count = 1; Count <= NumItems; ++Count) {
2531 4116 : if (WhichNumber == NodeConnections(Count).NodeNumber) {
2532 95 : ++CountOfItems;
2533 : }
2534 : }
2535 :
2536 63 : if (CountOfItems > 0) {
2537 :
2538 63 : AllNumbersInList.dimension(CountOfItems, 0);
2539 63 : CountOfItems = 0;
2540 :
2541 4179 : for (int Count = 1; Count <= NumItems; ++Count) {
2542 4116 : if (WhichNumber == NodeConnections(Count).NodeNumber) {
2543 95 : ++CountOfItems;
2544 95 : AllNumbersInList(CountOfItems) = Count;
2545 : }
2546 : }
2547 : }
2548 63 : }
2549 :
2550 : } // namespace EnergyPlus::BranchNodeConnections
|