10
@@ -1953,6 +2538,168 @@
1
+
+ True
+
+
+ True
+
+
+ True
+
+
+ Fill
+
+
+ 7, 6
+
+
+ 0, 0, 0, 0
+
+
+ 663, 483
+
+
+ 19
+
+
+ gridResults
+
+
+ System.Windows.Forms.DataGridView, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
+ TabPage1
+
+
+ 0
+
+
+ True
+
+
+ Propriedade
+
+
+ True
+
+
+ Valor
+
+
+ True
+
+
+ Unidade
+
+
+ True
+
+
+ True
+
+
+ True
+
+
+ True
+
+
+ Fill
+
+
+ 7, 6
+
+
+ 7, 6, 7, 6
+
+
+ 698, 482
+
+
+ 20
+
+
+ gridReactions
+
+
+ System.Windows.Forms.DataGridView, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
+ TabPage2
+
+
+ 0
+
+
+ True
+
+
+ Reação
+
+
+ True
+
+
+ Propriedade
+
+
+ True
+
+
+ Valor
+
+
+ True
+
+
+ Unidade
+
+
+ True
+
+
+ True
+
+
+ Fill
+
+
+ 0, 0
+
+
+ 7, 6, 7, 6
+
+
+ 712, 494
+
+
+ 0
+
+
+ gridConversions
+
+
+ System.Windows.Forms.DataGridView, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089
+
+
+ TabPage3
+
+
+ 0
+
+
+ True
+
+
+ Componente
+
+
+ True
+
+
+ Conversão (%)
+
True
@@ -1960,17 +2707,20 @@
25
- 6, 13
+ 13, 26
True
- 355, 1032
+ 769, 1759
Microsoft Sans Serif, 8.25pt
+
+ 7, 6, 7, 6
+
EditingForm_PFR_Reactor
diff --git a/DWSIM.UnitOperations/Editing Forms/EditingForm_ReactorPFR.vb b/DWSIM.UnitOperations/Editing Forms/EditingForm_ReactorPFR.vb
index d97d3b7d..73bbc95d 100644
--- a/DWSIM.UnitOperations/Editing Forms/EditingForm_ReactorPFR.vb
+++ b/DWSIM.UnitOperations/Editing Forms/EditingForm_ReactorPFR.vb
@@ -514,14 +514,14 @@ Public Class EditingForm_ReactorPFR
i = 0
Do
color1 = Color.FromArgb(255, rnd.Next(0, 255), rnd.Next(0, 255), rnd.Next(0, 255))
- With .AddCurve(vn(i), su.Converter.ConvertArrayFromSI(units.volume, vx), su.Converter.ConvertArrayFromSI(units.molar_conc, vya(i)), color1, ZedGraph.SymbolType.Circle)
+ With .AddCurve(vn(i), su.Converter.ConvertArrayFromSI(units.distance, vx), su.Converter.ConvertArrayFromSI(units.molar_conc, vya(i)), color1, ZedGraph.SymbolType.Circle)
.Line.IsSmooth = True
.Symbol.IsVisible = False
End With
i += 1
Loop Until i = vn.Length - 1
color1 = Color.FromArgb(255, rnd.Next(0, 255), rnd.Next(0, 255), rnd.Next(0, 255))
- With .AddCurve("T / " & units.temperature, su.Converter.ConvertArrayFromSI(units.volume, vx), su.Converter.ConvertArrayFromSI(units.temperature, vya(i)), color1, ZedGraph.SymbolType.Circle)
+ With .AddCurve("T / " & units.temperature, su.Converter.ConvertArrayFromSI(units.distance, vx), su.Converter.ConvertArrayFromSI(units.temperature, vya(i)), color1, ZedGraph.SymbolType.Circle)
.Line.IsSmooth = True
.Symbol.IsVisible = False
.IsY2Axis = True
@@ -534,7 +534,7 @@ Public Class EditingForm_ReactorPFR
.IsY2Axis = True
.YAxisIndex = 1
End With
- .XAxis.Title.Text = "V / " & units.volume
+ .XAxis.Title.Text = "Reactor Length / " & units.distance
.XAxis.Title.FontSpec.Size = 16
.XAxis.Scale.FontSpec.Size = 16
.XAxis.Scale.MaxAuto = False
diff --git a/DWSIM.UnitOperations/Reactors/CSTR.vb b/DWSIM.UnitOperations/Reactors/CSTR.vb
index 5aecde77..096a8f41 100644
--- a/DWSIM.UnitOperations/Reactors/CSTR.vb
+++ b/DWSIM.UnitOperations/Reactors/CSTR.vb
@@ -33,6 +33,8 @@ Namespace Reactors
Inherits Reactor
+ Private _IObj As InspectorItem
+
Public Enum EReactorMode
SingleOutlet
TwoOutlets
@@ -289,6 +291,22 @@ Namespace Reactors
IObj?.SetCurrent()
+ IObj?.Paragraphs.Add("To run a simulation of a reactor, the user needs to define the chemical reactions which will take place in the reactor.
+ This Is done through the Reactions Manager, accessible through Simulation Settings > Basis > Open Chemical Reactions Manager or Tools > Reactions Manager menus (see separate documentation).
Reactions can be of Equilibrium, Conversion, Kinetic or Heterogeneous Catalytic types. One or more reactions can be combined to define
+ a Reaction Set. The reactors then 'see' the reactions through the reaction sets.
+
Equilibrium
+ Reactions are defined by an equilibrium constant (K). The source Of
+ Information for the equilibrium constant can be a direct gibbs energy
+ calculation, an expression defined by the user Or a constant value.
+ Equilibrium Reactions can be used in Equilibrium And Gibbs reactors.
Conversion
+ Reactions are defined by the amount of a base compound which Is
+ consumed in the reaction. This amount can be a fixed value Or a
+ Function of() the system temperature. Conversion reactions are supported
+ by the Conversion reactor.
Kinetic reactions are reactions defined by a kinetic expression. These reactions are supported by the PFR and CSTR reactors.
Heterogeneous Catalytic reactions in DWSIM must obey the Langmuir–Hinshelwood
+ mechanism, where compounds react over a solid catalyst surface. In this
+ model, Reaction rates are a function of catalyst amount (i.e. mol/kg
+ cat.s). These Reactions are supported by the PFR And CStr reactors.")
+
'ims-stream (internal material stream) to be used during internal calculations
'Clone inlet stream as initial estimation
ims = DirectCast(FlowSheet.SimulationObjects(Me.GraphicObject.InputConnectors(0).AttachedConnector.AttachedFrom.Name), MaterialStream).Clone
@@ -347,7 +365,7 @@ Namespace Reactors
'Check Reaction type, Base components and reaction volume
If FlowSheet.ReactionSets(Me.ReactionSetID).Reactions.Count = 0 Then Throw New Exception("No reaction defined")
- ErrCode = "No kinetic or catalytic reaction found"
+ ErrCode = "No kinetic Or catalytic reaction found"
For Each rxnsb As ReactionSetBase In FlowSheet.ReactionSets(Me.ReactionSetID).Reactions.Values
rxn = FlowSheet.Reactions(rxnsb.ReactionID)
If (rxn.ReactionType = ReactionType.Kinetic Or rxn.ReactionType = ReactionType.Heterogeneous_Catalytic) And rxnsb.IsActive Then
@@ -1490,7 +1508,7 @@ out: Dim ms1, ms2 As MaterialStream
Dim str As New Text.StringBuilder
- str.AppendLine("Reactor: " & Me.GraphicObject.Tag)
+ str.AppendLine("Reactor: " & Me.GraphicObject.Tag)
str.AppendLine("Property Package: " & Me.PropertyPackage.ComponentName)
str.AppendLine()
str.AppendLine("Calculation Parameters")
diff --git a/DWSIM.UnitOperations/Reactors/Conversion.vb b/DWSIM.UnitOperations/Reactors/Conversion.vb
index d3afd813..d3d15302 100644
--- a/DWSIM.UnitOperations/Reactors/Conversion.vb
+++ b/DWSIM.UnitOperations/Reactors/Conversion.vb
@@ -118,6 +118,22 @@ Namespace Reactors
IObj?.SetCurrent()
+ IObj?.Paragraphs.Add("To run a simulation of a reactor, the user needs to define the chemical reactions which will take place in the reactor.
+ This Is done through the Reactions Manager, accessible through Simulation Settings > Basis > Open Chemical Reactions Manager or Tools > Reactions Manager menus (see separate documentation).
Reactions can be of Equilibrium, Conversion, Kinetic or Heterogeneous Catalytic types. One or more reactions can be combined to define
+ a Reaction Set. The reactors then 'see' the reactions through the reaction sets.
+
Equilibrium
+ Reactions are defined by an equilibrium constant (K). The source Of
+ Information for the equilibrium constant can be a direct gibbs energy
+ calculation, an expression defined by the user Or a constant value.
+ Equilibrium Reactions can be used in Equilibrium And Gibbs reactors.
Conversion
+ Reactions are defined by the amount of a base compound which Is
+ consumed in the reaction. This amount can be a fixed value Or a
+ Function of() the system temperature. Conversion reactions are supported
+ by the Conversion reactor.
Kinetic reactions are reactions defined by a kinetic expression. These reactions are supported by the PFR and CSTR reactors.
Heterogeneous Catalytic reactions in DWSIM must obey the Langmuir–Hinshelwood
+ mechanism, where compounds react over a solid catalyst surface. In this
+ model, Reaction rates are a function of catalyst amount (i.e. mol/kg
+ cat.s). These Reactions are supported by the PFR And CStr reactors.")
+
Validate()
InitVars()
diff --git a/DWSIM.UnitOperations/Reactors/PFR.vb b/DWSIM.UnitOperations/Reactors/PFR.vb
index 166ab272..f668fcd8 100644
--- a/DWSIM.UnitOperations/Reactors/PFR.vb
+++ b/DWSIM.UnitOperations/Reactors/PFR.vb
@@ -35,6 +35,8 @@ Namespace Reactors
Inherits Reactor
+ Private _IObj As InspectorItem
+
Protected m_vol As Double
Protected m_dv As Double = 0.01
@@ -122,6 +124,21 @@ Namespace Reactors
Public Function ODEFunc(ByVal x As Double, ByVal y As Double()) As Double()
+ _IObj?.SetCurrent
+
+ Dim IObj2 As Inspector.InspectorItem = Inspector.Host.GetNewInspectorItem()
+
+ Inspector.Host.CheckAndAdd(IObj2, "", "ODEFunc", "ODE solver for reactor concentrations", "", True)
+
+ IObj2?.SetCurrent
+
+ IObj2?.Paragraphs.Add("
Input Vars
")
+
+ IObj2?.Paragraphs.Add(String.Format("Volume Step: {0}", x))
+ IObj2?.Paragraphs.Add(String.Format("Compound Mole Flows: {0} mol/s", y.ToMathArrayString))
+
+ IObj2?.Paragraphs.Add("Intermediate Calcs
")
+
Dim conv As New SystemsOfUnits.Converter
Dim i As Integer = 0
@@ -131,10 +148,16 @@ Namespace Reactors
j = 0
For Each s As String In N00.Keys
- C(s) = y(j) * ResidenceTime / (Volume * VolumeFraction)
+ If y(j) < 0 Then
+ C(s) = 0.0#
+ Else
+ C(s) = y(j) * ResidenceTime / (Volume * VolumeFraction)
+ End If
j = j + 1
Next
+ IObj2?.Paragraphs.Add(String.Format("Compound Concentrations: {0} mol/m3", C.Values.ToArray.ToMathArrayString))
+
'conversion factors for different basis other than molar concentrations
Dim convfactors As New Dictionary(Of String, Double)
@@ -154,13 +177,18 @@ Namespace Reactors
i = 0
Do
+
'process reaction i
rxn = FlowSheet.Reactions(ar(i))
BC = rxn.BaseReactant
scBC = rxn.Components(BC).StoichCoeff
+ IObj2?.Paragraphs.Add(String.Format("Reaction ID: {0}", rxn.Name))
+
Dim T As Double = ims.Phases(0).Properties.temperature.GetValueOrDefault
+ IObj2?.Paragraphs.Add(String.Format("T: {0} K", T))
+
Dim rx As Double = 0.0#
convfactors = Me.GetConvFactors(rxn, ims)
@@ -187,6 +215,8 @@ Namespace Reactors
rx = kxf * rxf - kxr * rxr
+ IObj2?.Paragraphs.Add(String.Format("Reaction Rate: {0} {1}", rx, rxn.VelUnit))
+
Rxi(rxn.ID) = SystemsOfUnits.Converter.ConvertToSI(rxn.VelUnit, rx)
Kf(i) = kxf
@@ -215,12 +245,15 @@ Namespace Reactors
For Each sb As ReactionStoichBase In rxn.Components.Values
If sb.StoichCoeff < 0 Then
+ IObj2?.Paragraphs.Add(String.Format("R{0} ({1}): {2} {3}", ir.ToString, sb.CompName, C(sb.CompName) * convfactors(sb.CompName), rxn.ConcUnit))
rxn.ExpContext.Variables.Add("R" & ir.ToString, C(sb.CompName) * convfactors(sb.CompName))
ir += 1
ElseIf sb.StoichCoeff > 0 Then
+ IObj2?.Paragraphs.Add(String.Format("P{0} ({1}): {2} {3}", ip.ToString, sb.CompName, C(sb.CompName) * convfactors(sb.CompName), rxn.ConcUnit))
rxn.ExpContext.Variables.Add("P" & ip.ToString, C(sb.CompName) * convfactors(sb.CompName))
ip += 1
Else
+ IObj2?.Paragraphs.Add(String.Format("N{0} ({1}): {2} {3}", ine.ToString, sb.CompName, C(sb.CompName) * convfactors(sb.CompName), rxn.ConcUnit))
rxn.ExpContext.Variables.Add("N" & ine.ToString, C(sb.CompName) * convfactors(sb.CompName))
ine += 1
End If
@@ -234,10 +267,15 @@ Namespace Reactors
denmval = rxn.Expr.Evaluate
+ IObj2?.Paragraphs.Add(String.Format("Numerator Value: {0}", numval))
+ IObj2?.Paragraphs.Add(String.Format("Denominator Value: {0}", denmval))
+
rx = numval / denmval
End If
+ IObj2?.Paragraphs.Add(String.Format("Reaction Rate: {0} {1}", rx, rxn.VelUnit))
+
Rxi(rxn.ID) = SystemsOfUnits.Converter.ConvertToSI(rxn.VelUnit, rx)
End If
@@ -266,6 +304,14 @@ Namespace Reactors
FlowSheet.CheckStatus()
+ IObj2?.Paragraphs.Add("Results
")
+
+ IObj2?.Paragraphs.Add(String.Format("Compound Mole Flows Variation: {0} mol/[m3.s]", dy.ToMathArrayString))
+
+ IObj2?.Close()
+
+ If Double.IsNaN(dy.Sum) Then Throw New Exception("PFR ODE solver failed to find a solution.")
+
Return dy
End Function
@@ -278,6 +324,22 @@ Namespace Reactors
IObj?.SetCurrent()
+ IObj?.Paragraphs.Add("To run a simulation of a reactor, the user needs to define the chemical reactions which will take place in the reactor.
+ This Is done through the Reactions Manager, accessible through Simulation Settings > Basis > Open Chemical Reactions Manager or Tools > Reactions Manager menus (see separate documentation).
Reactions can be of Equilibrium, Conversion, Kinetic or Heterogeneous Catalytic types. One or more reactions can be combined to define
+ a Reaction Set. The reactors then 'see' the reactions through the reaction sets.
+
Equilibrium
+ Reactions are defined by an equilibrium constant (K). The source Of
+ Information for the equilibrium constant can be a direct gibbs energy
+ calculation, an expression defined by the user Or a constant value.
+ Equilibrium Reactions can be used in Equilibrium And Gibbs reactors.
Conversion
+ Reactions are defined by the amount of a base compound which Is
+ consumed in the reaction. This amount can be a fixed value Or a
+ Function of() the system temperature. Conversion reactions are supported
+ by the Conversion reactor.
Kinetic reactions are reactions defined by a kinetic expression. These reactions are supported by the PFR and CSTR reactors.
Heterogeneous Catalytic reactions in DWSIM must obey the Langmuir–Hinshelwood
+ mechanism, where compounds react over a solid catalyst surface. In this
+ model, Reaction rates are a function of catalyst amount (i.e. mol/kg
+ cat.s). These Reactions are supported by the PFR And CStr reactors.")
+
N00 = New Dictionary(Of String, Double)
C0 = New Dictionary(Of String, Double)
C = New Dictionary(Of String, Double)
@@ -386,6 +448,16 @@ Namespace Reactors
Dim prevvol As Double = 0.0#
Do
+ IObj?.SetCurrent
+
+ Dim IObj2 As Inspector.InspectorItem = Inspector.Host.GetNewInspectorItem()
+
+ Inspector.Host.CheckAndAdd(IObj2, "", "Calculate", String.Format("PFR Volume Step Calculation (V = {0} m3)", currvol), "", True)
+
+ IObj2?.SetCurrent()
+
+ _IObj = IObj2
+
C = New Dictionary(Of String, Double)
C0 = New Dictionary(Of String, Double)
@@ -475,16 +547,18 @@ Namespace Reactors
Next
Dim odesolver = New DotNumerics.ODE.OdeImplicitRungeKutta5()
- 'odesolver.RelTol = 0.000001
- 'odesolver.AbsTol = 0.0000000001
+ odesolver.RelTol = 0.000001
+ odesolver.AbsTol = 0.0000000001
odesolver.InitializeODEs(AddressOf ODEFunc, N.Count)
- odesolver.Solve(vc, 0.0#, 0.05 * dV * Volume, dV * Volume, Sub(x As Double, y As Double()) vc = y)
+ IObj2?.SetCurrent
+ odesolver.Solve(vc, 0.0#, 0.1 * dV * Volume, dV * Volume, Sub(x As Double, y As Double()) vc = y)
If Double.IsNaN(vc.Sum) Then Throw New Exception(FlowSheet.GetTranslatedString("PFRMassBalanceError"))
C.Clear()
i = 0
For Each sb As KeyValuePair(Of String, Double) In C0
+ If vc(i) < 0.0# Then vc(i) = 0.0#
C(sb.Key) = Convert.ToDouble(vc(i) * ResidenceTime / Volume / VolumeFraction)
i = i + 1
Next
@@ -529,7 +603,7 @@ Namespace Reactors
DHr += rxn.ReactionHeat * Abs(Rxi(rxn.ID)) / 1000 * CatalystLoading * dV * Volume
End If
- If Ri.Values.Sum = 0.0# Then DHr = 0.0#
+ 'If Ri.Values.Sum = 0.0# Then DHr = 0.0#
i += 1
@@ -617,7 +691,7 @@ Namespace Reactors
'add data to array
Dim tmparr(C.Count + 2) As Double
- tmparr(0) = currvol
+ tmparr(0) = currvol / Volume * Length
i = 1
For Each d As Double In Me.C.Values
tmparr(i) = d
@@ -682,7 +756,7 @@ Namespace Reactors
prevvol = currvol
currvol += dV * Volume
- Loop Until (currvol - Volume) >= dV
+ Loop Until (currvol - Volume) >= Volume
Me.DeltaP = P0 - P
@@ -696,9 +770,13 @@ Namespace Reactors
Do
'process reaction i
+
rxn = FlowSheet.Reactions(ar(i))
- RxiT.Add(rxn.ID, (N(rxn.BaseReactant) - N00(rxn.BaseReactant)) / rxn.Components(rxn.BaseReactant).StoichCoeff / 1000 * Rxi(rxn.ID) / Ri(rxn.BaseReactant))
+ Dim f = Rxi(rxn.ID) / Ri(rxn.BaseReactant)
+ If Double.IsNaN(f) Or Double.IsInfinity(f) Then f = 1.0#
+
+ RxiT.Add(rxn.ID, (N(rxn.BaseReactant) - N00(rxn.BaseReactant)) / rxn.Components(rxn.BaseReactant).StoichCoeff / 1000 * f)
DHRi.Add(rxn.ID, rxn.ReactionHeat * RxiT(rxn.ID))
i += 1