Nodes of different colours represent the following:
Solid arrows point from a parent (sub)module to the submodule which is descended from it. Dashed arrows point from a module being used to the module or program unit using it. Where possible, edges connecting nodes are given different colours to make them easier to distinguish in large graphs.
Type | Intent | Optional | Attributes | Name | ||
---|---|---|---|---|---|---|
integer, | intent(in) | :: | GeneratorNum | |||
logical, | intent(in) | :: | RunFlag | |||
real(kind=r64), | intent(in) | :: | myload | |||
logical, | intent(in) | :: | FirstHVACIteration |
Nodes of different colours represent the following:
Solid arrows point from a procedure to one which it calls. Dashed arrows point from an interface to procedures which implement that interface. This could include the module procedures in a generic interface or the implementation in a submodule of an interface in a parent module. Where possible, edges connecting nodes are given different colours to make them easier to distinguish in large graphs.
Nodes of different colours represent the following:
Solid arrows point from a procedure to one which it calls. Dashed arrows point from an interface to procedures which implement that interface. This could include the module procedures in a generic interface or the implementation in a submodule of an interface in a parent module. Where possible, edges connecting nodes are given different colours to make them easier to distinguish in large graphs.
SUBROUTINE CalcICEngineGeneratorModel(GeneratorNum,RunFlag,MyLoad,FirstHVACIteration)
! SUBROUTINE INFORMATION:
! AUTHOR Dan Fisher
! DATE WRITTEN Sept. 2000
! MODIFIED na
! RE-ENGINEERED
! PURPOSE OF THIS SUBROUTINE:
! simulate a IC ENGINE generator using the BLAST model
! METHODOLOGY EMPLOYED:
! curve fit of performance data:
! REFERENCES:na
! USE STATEMENTS:
USE DataHVACGlobals, ONLY : FirstTimeStepSysFlag,TimeStepSys
USE CurveManager, ONLY : CurveValue
USE FluidProperties, ONLY : GetSpecificHeatGlycol
USE DataPlant, ONLY : PlantLoop
IMPLICIT NONE
! SUBROUTINE ARGUMENT DEFINITIONS:
INTEGER, INTENT(IN) :: GeneratorNum ! Generator number
LOGICAL, INTENT(IN) :: RunFlag ! TRUE when Generator operating
REAL(r64) , INTENT(IN) :: myload ! Generator demand
LOGICAL, INTENT(IN) :: FirstHVACIteration
! SUBROUTINE PARAMETER DEFINITIONS:
REAL(r64), PARAMETER :: ExhaustCP = 1.047d0 !Exhaust Gas Specific Heat (J/kg-K)
REAL(r64), PARAMETER :: KJtoJ = 1000.d0 !convert Kjoules to joules
! DERIVED TYPE DEFINITIONS
! SUBROUTINE LOCAL VARIABLE DECLARATIONS:
REAL(r64) :: MinPartLoadRat ! min allowed operating frac full load
REAL(r64) :: MaxPartLoadRat ! max allowed operating frac full load
REAL(r64) :: PLR ! Generator operating part load ratio
REAL(r64) :: RatedPowerOutput ! Generator nominal capacity (W)
REAL(r64) :: ElecPowerGenerated ! Generator output (W)
REAL(r64) :: ElectricEnergyGen ! Generator output (J)
! Special variables for IC ENGINE Generator
REAL(r64) :: MaxExhaustperPowerOutput !curve fit parameter
REAL(r64) :: ElecOutputFuelRat !(RELDC) Ratio of generator output to Fuel Energy Input
REAL(r64) :: RecJacHeattoFuelRat !(RJACDC) Ratio of Recoverable Jacket Heat to Fuel Energy Input
REAL(r64) :: RecLubeHeattoFuelRat !(RLUBDC) Ratio of Recoverable Lube Oil Heat to Fuel Energy Input
REAL(r64) :: TotExhausttoFuelRat !(REXDC) Total Exhaust Energy Input to Fuel Energy Input
REAL(r64) :: ExhaustTemp !(TEX) Exhaust Gas Temp
REAL(r64) :: UA !(UACDC) exhaust gas Heat Exchanger UA
REAL(r64) :: FuelEnergyUseRate ! IC ENGINE fuel use rate (W)
REAL(r64) :: FuelEnergyUsed ! IC ENGINE fuel use (J)
REAL(r64) :: QTotalHeatRecovered
REAL(r64) :: QJacketRec ! water jacket heat recovered (W)
REAL(r64) :: QLubeOilRec ! lube oil cooler heat recovered (W)
REAL(r64) :: QExhaustRec ! exhaust gas heat recovered (W)
REAL(r64) :: JacketEnergyRec ! water jacket heat recovered (J)
REAL(r64) :: LubeOilEnergyRec ! lube oil cooler heat recovered (J)
REAL(r64) :: ExhaustEnergyRec ! exhaust gas heat recovered (J)
REAL(r64) :: QExhaustTotal ! total engine exhaust heat (W)
REAL(r64) :: ExhaustGasFlow ! exhaust gas mass flow rate (kg/s)
REAL(r64) :: ExhaustStackTemp ! engine stack temp. (C)
REAL(r64) :: DesignMinExitGasTemp ! design engine stact saturated steam temp. (C)
REAL(r64) :: FuelHeatingValue !Heating Value of Fuel in kJ/kg
INTEGER :: HeatRecInNode !Heat Recovery Fluid Inlet Node Num
REAL(r64) :: HeatRecInTemp !Heat Recovery Fluid Inlet Temperature (C)
REAL(r64) :: HeatRecMdot !Heat Recovery Fluid Mass FlowRate (kg/s)
REAL(r64) :: HeatRecCp !Specific Heat of the Heat Recovery Fluid (J/kg-K)
REAL(r64) :: HRecRatio !When Max Temp is reached the amount of recovered heat has to be reduced.
! and this assumption uses this ratio to accomplish this task.
! LOAD LOCAL VARIABLES FROM DATA STRUCTURE (for code readability)
MinPartLoadRat = ICEngineGenerator(GeneratorNum)%MinPartLoadRat
MaxPartLoadRat = ICEngineGenerator(GeneratorNum)%MaxPartLoadRat
RatedPowerOutput = ICEngineGenerator(GeneratorNum)%RatedPowerOutput
MaxExhaustperPowerOutput = ICEngineGenerator(GeneratorNum)%MaxExhaustperPowerOutput
IF (ICEngineGenerator(GeneratorNum)%HeatRecActive) THEN
HeatRecInNode = ICEngineGenerator(GeneratorNum)%HeatRecInletNodeNum
HeatRecInTemp = Node(HeatRecInNode)%Temp
HeatRecCp = GetSpecificHeatGlycol(PlantLoop(ICEngineGenerator(GeneratorNum)%HRLoopNum)%FluidName, &
HeatRecInTemp, &
PlantLoop(ICEngineGenerator(GeneratorNum)%HRLoopNum)%FluidIndex, &
'CalcICEngineGeneratorModel')
HeatRecMdot = Node(HeatRecInNode)%MassFlowRate
ELSE
HeatRecInTemp = 0.0d0
HeatRecMdot = 0.0d0
ENDIF
!If no loop demand or Generator OFF, return
IF (.NOT. Runflag) THEN
ICEngineGenerator(GeneratorNum)%ElecPowerGenerated = 0.0d0
ICEngineGenerator(GeneratorNum)%ElecEnergyGenerated = 0.0d0
ICEngineGenerator(GeneratorNum)%HeatRecInletTemp = HeatRecInTemp
ICEngineGenerator(GeneratorNum)%HeatRecOutletTemp = HeatRecInTemp
ICEngineGenerator(GeneratorNum)%HeatRecMdotActual = 0.0d0
ICEngineGenerator(GeneratorNum)%QJacketRecovered = 0.0d0
ICEngineGenerator(GeneratorNum)%QExhaustRecovered = 0.0d0
ICEngineGenerator(GeneratorNum)%QLubeOilRecovered = 0.0d0
ICEngineGenerator(GeneratorNum)%QTotalHeatRecovered = 0.0d0
ICEngineGenerator(GeneratorNum)%JacketEnergyRec = 0.0d0
ICEngineGenerator(GeneratorNum)%ExhaustEnergyRec = 0.0d0
ICEngineGenerator(GeneratorNum)%LubeOilEnergyRec = 0.0d0
ICEngineGenerator(GeneratorNum)%TotalHeatEnergyRec = 0.0d0
ICEngineGenerator(GeneratorNum)%FuelEnergyUseRate = 0.0d0
ICEngineGenerator(GeneratorNum)%FuelEnergy = 0.0d0
ICEngineGenerator(GeneratorNum)%FuelMdot = 0.0d0
ICEngineGenerator(GeneratorNum)%ExhaustStackTemp = 0.0d0
RETURN
END IF
! CALCULATE POWER GENERATED AND PLR
ElecPowerGenerated = MIN(MyLoad,RatedPowerOutput)
ElecPowerGenerated = MAX(ElecPowerGenerated,0.0d0)
PLR = MIN(ElecPowerGenerated/RatedPowerOutput, MaxPartLoadRat)
PLR = MAX(PLR, MinPartLoadRat)
ElecPowerGenerated = PLR*RatedPowerOutput
!DETERMINE FUEL CONSUMED AND AVAILABLE WASTE HEAT
!Use Curve fit to determine Fuel Energy Input. For electric power generated in Watts, the fuel
!energy input is calculated in J/s. The PLBasedFuelInputCurve selects ratio of fuel flow (J/s)/power generated (J/s).
IF (PLR > 0.0d0)THEN
ElecOutputFuelRat = CurveValue(ICEngineGenerator(GeneratorNum)%ElecOutputFuelCurve, PLR)
FuelEnergyUseRate = ElecPowerGenerated / ElecOutputFuelRat
ELSE
FuelEnergyUseRate = 0.0d0
END IF
!Use Curve fit to determine heat recovered in the water jacket. This curve calculates the water jacket heat recovered (J/s) by
!multiplying the total fuel input (J/s) by the fraction of that power that could be recovered in the water jacket at that
!particular part load.
RecJacHeattoFuelRat = CurveValue(ICEngineGenerator(GeneratorNum)%RecJacHeattoFuelCurve, PLR)
QJacketRec = FuelEnergyUseRate * RecJacHeattoFuelRat
!Use Curve fit to determine Heat Recovered Lubricant heat. This curve calculates the lube heat recovered (J/s) by
!multiplying the total fuel input (J/s) by the fraction of that power that could be recovered in the lube oil at that
!particular part load.
RecLubeHeattoFuelRat = CurveValue(ICEngineGenerator(GeneratorNum)%RecLubeHeattoFuelCurve, PLR)
QLubeOilRec = FuelEnergyUseRate * RecLubeHeattoFuelRat
!Use Curve fit to determine Heat Recovered from the exhaust. This curve calculates the heat recovered (J/s) by
!multiplying the total fuel input (J/s) by the fraction of that power that could be recovered in the exhaust at that
!particular part load.
TotExhausttoFuelRat = CurveValue(ICEngineGenerator(GeneratorNum)%TotExhausttoFuelCurve, PLR)
QExhaustTotal = FuelEnergyUseRate * TotExhausttoFuelRat
!Use Curve fit to determine Exhaust Temperature in C. The temperature is simply a curve fit
!of the exhaust temperature in C to the part load ratio.
IF (PLR > 0.0d0)THEN
ExhaustTemp = CurveValue(ICEngineGenerator(GeneratorNum)%ExhaustTempCurve, PLR)
IF (ExhaustTemp > ReferenceTemp) THEN
ExhaustGasFlow = QExhaustTotal / (ExhaustCP*(ExhaustTemp-ReferenceTemp))
!Use Curve fit to determine stack temp after heat recovery
UA = ICEngineGenerator(GeneratorNum)%UACoef(1) * RatedPowerOutput ** &
ICEngineGenerator(GeneratorNum)%UACoef(2)
DesignMinExitGasTemp = ICEngineGenerator(GeneratorNum)%DesignMinExitGasTemp
ExhaustStackTemp = DesignMinExitGasTemp + (ExhaustTemp - DesignMinExitGasTemp) / &
EXP(UA/(MAX(ExhaustGasFlow, MaxExhaustperPowerOutput * RatedPowerOutput) * ExhaustCP))
QExhaustRec = MAX(ExhaustGasFlow*ExhaustCP*(ExhaustTemp-ExhaustStackTemp),0.0d0)
ELSE
IF (ICEngineGenerator(GeneratorNum)%ErrExhaustTempIndex == 0) THEN
CALL ShowWarningMessage('CalcICEngineGeneratorModel: '//trim(ICEngineGenerator(GeneratorNum)%TypeOf)// &
'="'//trim(ICEngineGenerator(GeneratorNum)%Name)//'" low Exhaust Temperature from Curve Value')
CALL ShowContinueError('...curve generated temperature=['//trim(RoundSigDigits(ExhaustTemp,3))// &
' C], PLR=['//trim(RoundSigDigits(PLR,3))//'].')
CALL ShowContinueError('...simulation will continue with exhaust heat reclaim set to 0.')
ENDIF
CALL ShowRecurringWarningErrorAtEnd('CalcICEngineGeneratorModel: '//trim(ICEngineGenerator(GeneratorNum)%TypeOf)// &
'="'//trim(ICEngineGenerator(GeneratorNum)%Name)//'" low Exhaust Temperature continues...', &
ICEngineGenerator(GeneratorNum)%ErrExhaustTempIndex,ReportMinOf=ExhaustTemp,ReportMaxOf=ExhaustTemp, &
ReportMaxUnits='[C]',ReportMinUnits='[C]')
QExhaustRec =0.0d0
ExhaustStackTemp = ICEngineGenerator(GeneratorNum)%DesignMinExitGasTemp
ENDIF
ELSE
QExhaustRec =0.0d0
END IF
QTotalHeatRecovered = QExhaustRec + QLubeOilRec + QJacketRec
IF (ICEngineGenerator(GeneratorNum)%HeatRecActive) THEN
CALL CalcICEngineGenHeatRecovery(GeneratorNum,QTotalHeatRecovered,HeatRecMDot,HRecRatio)
QExhaustRec = QExhaustRec*HRecRatio
QLubeOilRec = QLubeOilRec*HRecRatio
QJacketRec = QJacketRec*HRecRatio
QTotalHeatRecovered = QTotalHeatRecovered*HRecRatio
ELSE
ICEngineGenerator(GeneratorNum)%HeatRecInletTemp = HeatRecInTemp
ICEngineGenerator(GeneratorNum)%HeatRecOutletTemp = HeatRecInTemp
ICEngineGenerator(GeneratorNum)%HeatRecMdotActual = HeatRecMdot
ENDIF
!Calculate Energy
ElectricEnergyGen = ElecPowerGenerated*TimeStepSys*SecInHour
FuelEnergyUsed = FuelEnergyUseRate*TimeStepSys*SecInHour
JacketEnergyRec = QJacketRec*TimeStepSys*SecInHour
LubeOilEnergyRec = QLubeOilRec*TimeStepSys*SecInHour
ExhaustEnergyRec = QExhaustRec*TimeStepSys*SecInHour
ICEngineGenerator(GeneratorNum)%ElecPowerGenerated = ElecPowerGenerated
ICEngineGenerator(GeneratorNum)%ElecEnergyGenerated = ElectricEnergyGen
ICEngineGenerator(GeneratorNum)%QJacketRecovered = QJacketRec
ICEngineGenerator(GeneratorNum)%QLubeOilRecovered = QLubeOilRec
ICEngineGenerator(GeneratorNum)%QExhaustRecovered = QExhaustRec
ICEngineGenerator(GeneratorNum)%QTotalHeatRecovered = QTotalHeatRecovered
ICEngineGenerator(GeneratorNum)%JacketEnergyRec = JacketEnergyRec
ICEngineGenerator(GeneratorNum)%LubeOilEnergyRec = LubeOilEnergyRec
ICEngineGenerator(GeneratorNum)%ExhaustEnergyRec = ExhaustEnergyRec
ICEngineGenerator(GeneratorNum)%QTotalHeatRecovered = (QExhaustRec + QLubeOilRec + QJacketRec)
ICEngineGenerator(GeneratorNum)%TotalHeatEnergyRec = (ExhaustEnergyRec + LubeOilEnergyRec + JacketEnergyRec)
ICEngineGenerator(GeneratorNum)%FuelEnergyUseRate = ABS(FuelEnergyUseRate)
ICEngineGenerator(GeneratorNum)%FuelEnergy = ABS(FuelEnergyUsed)
FuelHeatingValue = ICEngineGenerator(GeneratorNum)%FuelHeatingValue
ICEngineGenerator(GeneratorNum)%FuelMdot = ABS(FuelEnergyUseRate)/(FuelHeatingValue * KJtoJ)
ICEngineGenerator(GeneratorNum)%ExhaustStackTemp = ExhaustStackTemp
RETURN
END SUBROUTINE CalcICEngineGeneratorModel