/[ascend]/trunk/models/johnpye/fprops/rankine_fprops.a4c
ViewVC logotype

Contents of /trunk/models/johnpye/fprops/rankine_fprops.a4c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2301 - (show annotations) (download) (as text)
Sat Aug 21 13:28:35 2010 UTC (13 years, 9 months ago) by jpye
File MIME type: text/x-ascend
File size: 21370 byte(s)
Regen toluene model working, next water.
1 (* ASCEND modelling environment
2 Copyright (C) 2007, 2008, 2009, 2010 Carnegie Mellon University
3
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2, or (at your option)
7 any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 59 Temple Place - Suite 330,
17 Boston, MA 02111-1307, USA.
18 *)(*
19 A number of Rankine-cycle (steam turbine power cycle) models of increasing
20 complexity, following the general development of Moran & Shapiro, Çengel,
21 and others.
22
23 Author: John Pye
24 *)
25
26 REQUIRE "atoms.a4l";
27 REQUIRE "johnpye/thermo_types.a4c";
28
29 IMPORT "johnpye/fprops/helmholtz";
30 IMPORT "sensitivity/solve";
31 IMPORT "johnpye/extpy/extpy";
32 IMPORT "johnpye/fprops/cycle_plot";
33
34 (*------------------------------------------------------------------------------
35 BACKGROUND STUFF
36 *)
37
38 MODEL fluid;
39 component IS_A symbol_constant;
40 END fluid;
41
42 (*
43 Thermo properties -- IAPWS-IF97
44 *)
45 MODEL stream_state;
46 cd IS_A fluid;
47 p IS_A pressure;
48 h IS_A specific_enthalpy;
49
50 T IS_A temperature;
51 v IS_A specific_volume;
52 s IS_A specific_entropy;
53 x IS_A fraction;
54
55 (*calc_vT: helmholtz_phsx_vT(
56 v, T : INPUT;
57 p, h, s, x : OUTPUT;
58 cd : DATA
59 );*)
60 calc_ph: helmholtz_Tvsx_ph(
61 p, h : INPUT;
62 T, v, s, x : OUTPUT;
63 cd : DATA
64 );
65 METHODS
66 METHOD default;
67 p := 10{bar};
68 p.nominal := 42 {bar};
69 IF cd.component == 'water' THEN
70 h := 2000 {kJ/kg};
71 ELSE
72 IF cd.component == 'carbondioxide' THEN
73 h := 350 {kJ/kg};
74 ELSE
75 h := 350 {kJ/kg};
76 END IF;
77 END IF;
78
79 T := 400 {K};
80 v.nominal := 10 {L/kg};
81 s := 4 {kJ/kg/K};
82 x := 0.8;
83
84 RUN enable_ph;
85 END default;
86 METHOD default_self;
87 RUN default;
88 END default_self;
89 METHOD enable_vT;
90 FOR i IN [1..4] DO
91 (*calc_ph[i].included := FALSE;
92 calc_vT[i].included := TRUE;*)
93 calc_ph[i].included := TRUE;
94 END FOR;
95 END enable_vT;
96 METHOD enable_ph;
97 FOR i IN [1..4] DO
98 calc_ph[i].included := TRUE;
99 (*calc_vT[i].included := FALSE;*)
100 END FOR;
101 END enable_ph;
102 METHOD solve;
103 EXTERNAL do_solve(SELF);
104 END solve;
105 END stream_state;
106
107 MODEL stream_state_test REFINES stream_state;
108 cd.component :== 'water';
109 METHODS
110 METHOD on_load;
111 RUN default_all;
112 FIX p, h;
113 p := 10 {bar};
114 h := 2000 {kJ/kg};
115 SOLVER QRSlv;
116 OPTION convopt 'RELNOM_SCALE';
117 SOLVE;
118 ASSERT abs(T - 453.03 {K}) < 0.01 {K};
119 ASSERT abs(v - 0.119808 {m^3/kg}) < 0.0001 {m^3/kg};
120 ASSERT abs(x - 0.6142) < 0.0001;
121 ASSERT abs(s - 4.8696 {kJ/kg/K}) < 0.0001 {kJ/kg/K};
122 END on_load;
123 END stream_state_test;
124
125
126 MODEL stream_state_test_co2 REFINES stream_state;
127 cd.component :== 'carbondioxide';
128 METHODS
129 METHOD on_load;
130 RUN default_all;
131 h := 350 {kJ/kg};
132 FIX p, x;
133 p := 9 {kPa};
134 x := 1e-6;
135 SOLVER QRSlv;
136 OPTION convopt 'RELNOM_SCALE';
137 END on_load;
138 END stream_state_test_co2;
139
140
141 MODEL stream_state_test_toluene REFINES stream_state;
142 cd.component :== 'toluene';
143 METHODS
144 METHOD on_load;
145 RUN default_all;
146 FIX p, x;
147 p := 8 {kPa};
148 x := 1e-6;
149 SOLVER QRSlv;
150 OPTION convopt 'RELNOM_SCALE';
151 END on_load;
152 END stream_state_test_toluene;
153
154
155 (* a simple connector that includes calculation of steam properties *)
156 MODEL stream_node;
157 state IS_A stream_state;
158 cd ALIASES state.cd;
159 p ALIASES state.p;
160 h ALIASES state.h;
161 v ALIASES state.v;
162 T ALIASES state.T;
163 s ALIASES state.s;
164 x ALIASES state.x;
165 mdot IS_A mass_rate;
166 METHODS
167
168 METHOD default_self;
169 RUN state.default_self;
170 RUN default;
171 END default_self;
172
173 METHOD default;
174 mdot.nominal := 2 {kg/s};
175 END default;
176 METHOD solve;
177 EXTERNAL do_solve(SELF);
178 END solve;
179 METHOD on_load;
180 RUN default_all; RUN reset; RUN values;
181 FIX p,h;
182 END on_load;
183 END stream_node;
184
185 MODEL stream_equipment;
186 inlet "in: inlet steam stream" IS_A stream_node;
187 outlet "out: outlet steam stream" IS_A stream_node;
188 inlet.cd, outlet.cd ARE_THE_SAME;
189 inlet.mdot, outlet.mdot ARE_THE_SAME;
190 cd ALIASES inlet.cd;
191 mdot ALIASES inlet.mdot;
192 END stream_equipment;
193
194 (*------------------------------------------------------------------------------
195 PUMP COMPONENT
196 *)
197
198 MODEL pump_simple REFINES stream_equipment;
199 NOTES
200 'block' SELF {Simple model of a pump using isentropic efficiency}
201 END NOTES;
202
203 dp IS_A delta_pressure;
204 inlet.p + dp = outlet.p;
205
206 outlet_is IS_A stream_state;
207 outlet_is.p, outlet.p ARE_THE_SAME;
208 outlet_is.cd, outlet.cd ARE_THE_SAME;
209 outlet_is.s, inlet.s ARE_THE_SAME;
210 eta IS_A fraction;
211
212 eta_eq:eta * (inlet.h - outlet.h) = (inlet.h - outlet_is.h);
213
214 (* work done on the environment, will be negative *)
215 Wdot IS_A energy_rate;
216 Wdot_eq:Wdot = mdot * w;
217
218 w IS_A negative_specific_work;
219 w_eq:w = inlet.h - outlet.h;
220 METHODS
221 METHOD default_self;
222 RUN inlet.default_self;
223 RUN outlet.default_self;
224 RUN outlet_is.default_self;
225 END default_self;
226 END pump_simple;
227
228 MODEL pump_simple_test REFINES pump_simple;
229 cd.component :== 'water';
230 METHODS
231 METHOD on_load;
232 RUN default_self;
233 FIX inlet.p; inlet.p := 5 {bar};
234 FIX inlet.h; inlet.h := 400 {kJ/kg};
235 FIX outlet.p; outlet.p := 100 {bar};
236 FIX eta; eta := 0.65;
237 FIX mdot; mdot := 900 {t/d};
238
239 inlet.v := 0.97 {L/kg};
240 inlet.T := 300 {K};
241
242 SOLVER QRSlv;
243 OPTION convopt 'RELNOM_SCALE';
244 OPTION iterationlimit 200;
245 END on_load;
246 END pump_simple_test;
247
248 (*------------------------------------------------------------------------------
249 TURBINE COMPONENT
250 *)
251
252 MODEL turbine_simple REFINES stream_equipment;
253 NOTES
254 'block' SELF {Simple turbine model}
255 END NOTES;
256
257 dp IS_A delta_pressure;
258 inlet.p + dp = outlet.p;
259
260 outlet_is IS_A stream_state;
261 outlet_is.cd, outlet.cd ARE_THE_SAME;
262 outlet_is.p, outlet.p ARE_THE_SAME;
263 outlet_is.s, inlet.s ARE_THE_SAME;
264
265 eta IS_A fraction;
266 eta_eq:eta * (inlet.h - outlet_is.h) = (inlet.h - outlet.h);
267
268 (* work done on the environment, will be positive *)
269 Wdot IS_A energy_rate;
270 Wedot_eq:Wdot = mdot * w;
271
272 w IS_A positive_specific_work;
273 w_eq:w = inlet.h - outlet.h;
274 METHODS
275 METHOD default_self;
276 RUN inlet.default_self;
277 RUN outlet.default_self;
278 RUN outlet_is.default_self;
279 END default_self;
280 END turbine_simple;
281
282 MODEL turbine_simple_test REFINES turbine_simple;
283 cd.component :== 'water';
284 METHODS
285 METHOD on_load;
286 RUN default_self;
287 FIX inlet.p;
288 FIX inlet.h;
289 FIX outlet.p;
290 FIX eta;
291 FIX mdot;
292
293 inlet.p := 100 {bar};
294 inlet.h := 3000 {kJ/kg};
295 outlet.p := 5 {bar};
296 eta := 0.85;
297 mdot := 900 {t/d};
298 END on_load;
299 END turbine_simple_test;
300
301 (*------------------------------------------------------------------------------
302 BOILER COMPONENT
303 *)
304
305 (*
306 simple model assumes no pressure drop, but heating losses due to
307 flue gas temperature
308 *)
309 MODEL boiler_simple REFINES stream_equipment;
310 NOTES
311 'block' SELF {Simple boiler model}
312 END NOTES;
313
314 inlet.p, outlet.p ARE_THE_SAME;
315 Qdot_fuel IS_A energy_rate;
316
317 q IS_A specific_energy;
318 q = (outlet.h - inlet.h);
319
320 Qdot IS_A energy_rate;
321 Qdot = mdot * q;
322
323 eta IS_A fraction;
324 Qdot = eta * Qdot_fuel;
325 METHODS
326 METHOD default_self;
327 RUN inlet.default_self;
328 RUN outlet.default_self;
329 END default_self;
330 END boiler_simple;
331
332 MODEL boiler_simple_test REFINES boiler_simple;
333 cd.component :== 'water';
334 METHODS
335 METHOD on_load;
336 RUN default_self;
337 FIX inlet.p;
338 FIX inlet.h;
339 FIX eta;
340 FIX mdot;
341
342 inlet.p := 100 {bar};
343 inlet.h := 500 {kJ/kg};
344
345 eta := 0.8;
346 outlet.h := 3000 {kJ/kg};
347 mdot := 900 {t/d};
348 END on_load;
349 END boiler_simple_test;
350
351 (*------------------------------------------------------------------------------
352 CONDENSER COMPONENT
353 *)
354
355 (*
356 this is really simple (fluid props permitting): just work out the heat
357 that must be expelled to get the water down to a certain state
358 *)
359 MODEL condenser_simple REFINES stream_equipment;
360 NOTES
361 'block' SELF {Simple condenser model}
362 'inline' inlet {in: yahoooo}
363 END NOTES;
364
365 inlet.p, outlet.p ARE_THE_SAME;
366 Qdot IS_A energy_rate;
367
368 cons_en: Qdot = mdot * (outlet.h - inlet.h);
369 METHODS
370 METHOD default_self;
371 RUN inlet.default_self;
372 RUN outlet.default_self;
373 END default_self;
374 END condenser_simple;
375
376 MODEL condenser_simple_test REFINES condenser_simple;
377 cd.component :== 'water';
378 METHODS
379 METHOD on_load;
380 RUN default_self;
381 FIX inlet.p, inlet.x;
382 FIX outlet.h;
383 FIX mdot;
384
385 inlet.p := 5 {bar};
386 inlet.x := 0.95;
387 outlet.h := 500 {kJ/kg};
388 mdot := 900 {t/d};
389 END on_load;
390 END condenser_simple_test;
391
392 (*------------------------------------------------------------------------------
393 FEEDWATER HEATER
394 *)
395
396 (*
397 open heater does not have inlet.mdot==outlet.mdot, so not a refinement
398 of 'stream_equipment'.
399 *)
400 MODEL heater_open;
401 NOTES
402 'block' SELF {Simple open feedwater heater model}
403 END NOTES;
404
405 inlet "in:" IS_A stream_node;
406 inlet_heat "in:" IS_A stream_node;
407 outlet "out:" IS_A stream_node;
408 inlet_heat.p, inlet.p, outlet.p ARE_THE_SAME;
409 inlet.cd, outlet.cd, inlet_heat.cd ARE_THE_SAME;
410 cd ALIASES inlet.cd;
411
412 (* cons. mass *)
413 cons_mass: inlet.mdot + inlet_heat.mdot = outlet.mdot;
414
415 m_ratio IS_A factor;
416 inlet_heat.mdot = m_ratio * inlet.mdot;
417 (* cons. energy *)
418 cons_en: inlet.h + m_ratio * inlet_heat.h = outlet.h;
419 METHODS
420 METHOD default_self;
421 RUN inlet.default_self;
422 RUN inlet_heat.default_self;
423 RUN outlet.default_self;
424 END default_self;
425 END heater_open;
426
427 MODEL heater_open_test REFINES heater_open;
428 cd.component :== 'water';
429 METHODS
430 METHOD on_load;
431 RUN default_self;
432 FIX inlet.p, inlet.h;
433 inlet.p := 40 {bar};
434 inlet.h := 634 {kJ/kg};
435 FIX inlet_heat.h;
436 inlet_heat.h := 2960 {kJ/kg};
437
438 FIX outlet.mdot;
439 outlet.mdot := 900 {t/d};
440
441 FIX inlet.mdot;
442 inlet.mdot := 700 {t/d};
443 END on_load;
444 END heater_open_test;
445
446 MODEL heater_open2;
447 NOTES
448 'block' SELF {Simple open feedwater heater model}
449 END NOTES;
450
451 inlet "in:" IS_A stream_node;
452 inlet_heat1 "in:" IS_A stream_node;
453 inlet_heat2 "in:" IS_A stream_node;
454 outlet "out:" IS_A stream_node;
455 inlet.cd, inlet_heat1.cd, inlet_heat2.cd, outlet.cd ARE_THE_SAME;
456 inlet_heat1.p, inlet_heat2.p, inlet.p, outlet.p ARE_THE_SAME;
457 cd ALIASES inlet.cd;
458
459 (* cons. mass *)
460 cons_mass: inlet.mdot + inlet_heat1.mdot + inlet_heat2.mdot = outlet.mdot;
461
462 (* cons. energy *)
463 cons_en: inlet.mdot * inlet.h + inlet_heat1.mdot * inlet_heat1.h
464 + inlet_heat2.mdot * inlet_heat2.h = outlet.mdot * outlet.h;
465 METHODS
466 METHOD default_self;
467 RUN inlet.default_self;
468 RUN inlet_heat.default_self;
469 RUN inlet_heat2.default_self;
470 RUN outlet.default_self;
471 END default_self;
472 END heater_open2;
473
474 MODEL heater_closed;
475 NOTES
476 'block' SELF {Simple open feedwater heater model}
477 END NOTES;
478
479 inlet "in:" IS_A stream_node;
480 inlet_heat "in:" IS_A stream_node;
481 outlet "out:" IS_A stream_node;
482 outlet_heat "out:" IS_A stream_node;
483
484 inlet.cd, outlet.cd ARE_THE_SAME;
485 inlet_heat.cd, outlet_heat.cd ARE_THE_SAME;
486 cd ALIASES inlet.cd;
487 cd_heat ALIASES inlet_heat.cd;
488
489 inlet_heat.p, outlet_heat.p ARE_THE_SAME;
490 inlet.p, outlet.p ARE_THE_SAME;
491
492 Qdot "heat transferred to main flow stream" IS_A energy_rate;
493
494 q IS_A specific_energy;
495 Qdot = q * inlet.mdot;
496
497 (* cons. mass *)
498 cons_mass: inlet.mdot = outlet.mdot;
499 cons_mass_heat: inlet_heat.mdot = outlet_heat.mdot;
500
501 m_ratio IS_A factor;
502 inlet_heat.mdot = inlet.mdot * m_ratio;
503
504 (* cons. energy *)
505 cons_en: q + inlet.h = outlet.h;
506 cons_en_heat: m_ratio * inlet_heat.h = m_ratio * outlet_heat.h + q;
507 METHODS
508 METHOD default_self;
509 RUN inlet.default_self;
510 RUN inlet_heat.default_self;
511 RUN outlet.default_self;
512 RUN outlet_heat.default_self;
513 END default_self;
514 END heater_closed;
515
516 MODEL heater_closed_test REFINES heater_closed;
517 cd.component :== 'water';
518 cd_heat.component :== 'water';
519 METHODS
520 METHOD on_load;
521 FIX inlet.p, inlet.h, inlet.mdot;
522 inlet.p := 40 {bar};
523 inlet.h := 634 {kJ/kg};
524 inlet.mdot := 700 {t/d};
525
526 FIX inlet_heat.p, inlet_heat.h, inlet_heat.mdot;
527 inlet_heat.p := 50 {bar};
528 inlet_heat.h := 2960 {kJ/kg};
529 inlet_heat.mdot := 500 {t/d};
530
531 FIX outlet.h;
532 outlet.h := 900 {kJ/kg};
533
534 SOLVER QRSlv;
535 OPTION convopt 'RELNOM_SCALE';
536 OPTION iterationlimit 200;
537 END on_load;
538 END heater_closed_test;
539
540 (*------------------------------------------------------------------------------
541 TEE PIECE
542 *)
543
544 (*
545 it's not a car :-)
546 *)
547 MODEL tee;
548 NOTES
549 'block' SELF {Model of a branching of two flow streams}
550 END NOTES;
551
552 inlet "in:" IS_A stream_node;
553 outlet "out:" IS_A stream_node;
554 outlet_branch "out:" IS_A stream_node;
555
556 inlet.cd, outlet.cd, outlet_branch.cd ARE_THE_SAME;
557 cd ALIASES inlet.cd;
558
559 inlet.p, outlet.p, outlet_branch.p ARE_THE_SAME;
560 inlet.h, outlet.h, outlet_branch.h ARE_THE_SAME;
561
562 (* cons. mass *)
563 cons_mass: inlet.mdot = outlet.mdot + outlet_branch.mdot;
564
565 phi IS_A fraction;
566 phi_eq: phi * inlet.mdot = outlet_branch.mdot;
567
568 END tee;
569
570 (*------------------------------------------------------------------------------
571 OVERALL CYCLE
572 *)
573
574 (*
575 simplest possible rankine cycle
576 *)
577 MODEL rankine_common;
578
579 BO IS_A boiler_simple;
580 TU IS_A turbine_simple;
581 CO IS_A condenser_simple;
582 PU IS_A pump_simple;
583 cd ALIASES BO.cd;
584
585 BO.outlet, TU.inlet ARE_THE_SAME;
586 TU.outlet, CO.inlet ARE_THE_SAME;
587 CO.outlet, PU.inlet ARE_THE_SAME;
588 PU.outlet, BO.inlet ARE_THE_SAME;
589
590 Qdot_loss ALIASES CO.Qdot;
591 Wdot IS_A energy_rate;
592 Wdot = TU.Wdot + PU.Wdot;
593
594 T_H ALIASES BO.outlet.T;
595 T_C ALIASES CO.outlet.T;
596
597 eta IS_A fraction;
598 eta * (BO.Qdot_fuel) = TU.Wdot + PU.Wdot;
599
600 eta_carnot IS_A fraction;
601 eta_carnot = 1 - T_C / T_H;
602
603 DE_cycle "cycle energy balance, should be zero" IS_A energy_rate;
604 DE_cycle = BO.Qdot + CO.Qdot - TU.Wdot - PU.Wdot;
605
606 mdot ALIASES TU.mdot;
607 x_turb_out ALIASES TU.outlet.x;
608 METHODS
609 METHOD default_self;
610 RUN BO.default_self;
611 RUN TU.default_self;
612 RUN CO.default_self;
613 RUN PU.default_self;
614 END default_self;
615 METHOD cycle_plot;
616 EXTERNAL cycle_plot_rankine(SELF);
617 END cycle_plot;
618 END rankine_common;
619
620
621 MODEL rankine_water REFINES rankine_common;
622 cd.component :== 'water';
623 METHODS
624 (* first test case: just some plausible values *)
625 METHOD on_load;
626 RUN ClearAll;
627 RUN default_self;
628 FIX BO.eta; BO.eta := 1.0;
629 FIX TU.eta; TU.eta := 0.85;
630 FIX PU.eta; PU.eta := 0.8;
631 FIX Wdot; Wdot := 100 {MW};
632 (* FIX CO.outlet.p; CO.outlet.p := 10 {kPa};*)
633 FIX CO.outlet.T; CO.outlet.T := 40 {K} + 273.15 {K};
634 FIX CO.outlet.x; CO.outlet.x := 1e-6;
635 FIX PU.outlet.p; PU.outlet.p := 150 {bar};
636 PU.outlet.p.upper_bound := 150 {bar};
637 FIX BO.outlet.T; BO.outlet.T := 580 {K} + 273.15 {K};
638
639 SOLVER QRSlv;
640 OPTION convopt 'RELNOM_SCALE';
641 OPTION iterationlimit 200;
642 END on_load;
643 METHOD set_x_limit;
644 FREE PU.outlet.p;
645 PU.outlet.p.upper_bound := 150 {bar};
646 FIX TU.outlet.x; TU.outlet.x := 0.9;
647 END set_x_limit;
648 (*
649 second test case: numbers from Example 2.1, K Weston, 'Energy Conversion',
650 1992, http://www.personal.utulsa.edu/~kenneth-weston/
651 *)
652 METHOD specify;
653 RUN ClearAll;
654 FIX PU.outlet.p;
655 FIX BO.outlet.T;
656 FIX PU.inlet.p;
657 FIX CO.outlet.x;
658 FIX TU.eta;
659 FIX PU.eta;
660 FIX BO.eta;
661 FIX mdot;
662 END specify;
663 METHOD values;
664 PU.outlet.p := 2000 {psi};
665 BO.outlet.T := 1460 {R}; BO.outlet.h := 3400 {kJ/kg};
666 PU.inlet.p := 1 {psi};
667 CO.outlet.x := 1e-6; (*PU.inlet.h := 69.73 {btu/lbm};*)
668 TU.eta := 1.0;
669 PU.eta := 1.0;
670 BO.eta := 1.0;
671 mdot := 900 {t/d};
672 END values;
673 (*
674 METHOD on_load;
675 RUN default_self;
676 RUN specify;
677 RUN values;
678
679 SOLVER QRSlv;
680 OPTION convopt 'RELNOM_SCALE';
681 OPTION iterationlimit 200;
682 END on_load;
683 *)
684 METHOD self_test;
685 (* check the results against those from K Weston's book *)
686 (* note that we have NOT neglected pump work in this case! *)
687 ASSERT abs(eta - 0.4294) < 0.0030;
688 ASSERT abs(eta_carnot - 0.6152) < 0.0005;
689 ASSERT abs(TU.outlet.x - 0.7736) < 0.0005;
690 ASSERT abs(TU.w - 603.1 {btu/lbm}) < 0.7 {btu/lbm};
691 END self_test;
692 METHOD default_self;
693 RUN rankine_common::default_self;
694 BO.outlet.h := 3000 {kJ/kg}; (* guess *)
695 TU.outlet.h := 3000 {kJ/kg}; (* guess *)
696 CO.outlet.h := 200 {kJ/kg};
697 CO.outlet.p := 10 {kPa};
698 END default_self;
699 END rankine_water;
700
701 MODEL rankine_co2 REFINES rankine_common;
702 cd.component :== 'carbondioxide';
703 METHODS
704 METHOD on_load_1;
705 RUN ClearAll;
706 RUN default_self;
707 FIX BO.eta; BO.eta := 1.0;
708 FIX TU.eta; TU.eta := 0.85;
709 FIX PU.eta; PU.eta := 0.8;
710 FIX Wdot; Wdot := 100 {MW};
711 FIX CO.outlet.T; CO.outlet.T := 40 {K} + 273.15 {K};
712 FIX CO.outlet.p; CO.outlet.p := 80 {bar};
713 FIX PU.outlet.p; PU.outlet.p := 150 {bar};
714 FIX BO.outlet.T; BO.outlet.T := 580 {K} + 273.15 {K};
715
716 SOLVER QRSlv;
717 OPTION convopt 'RELNOM_SCALE';
718 OPTION iterationlimit 200;
719 END on_load_1;
720 METHOD on_load;
721 RUN ClearAll;
722 RUN default_self;
723 FIX BO.eta; BO.eta := 1.0;
724 FIX TU.eta; TU.eta := 0.85;
725 FIX PU.eta; PU.eta := 0.8;
726 FIX Wdot; Wdot := 100 {MW};
727 FIX CO.outlet.T; CO.outlet.T := 10 {K} + 273.15 {K};
728 FIX CO.outlet.x; CO.outlet.x := 1e-6;
729 FIX PU.outlet.p; PU.outlet.p := 150 {bar};
730 FIX BO.outlet.T; BO.outlet.T := 580 {K} + 273.15 {K};
731
732 SOLVER QRSlv;
733 OPTION convopt 'RELNOM_SCALE';
734 OPTION iterationlimit 200;
735 END on_load;
736 METHOD default_self;
737 RUN rankine_common::default_self;
738 BO.outlet.h := 350 {kJ/kg}; (* guess *)
739 TU.outlet.h := 1000 {kJ/kg}; (* guess *)
740 CO.outlet.h := 350 {kJ/kg};
741 CO.outlet.p := 60 {bar};
742 CO.outlet.p.lower_bound := 5.2 {bar};
743 END default_self;
744 END rankine_co2;
745
746 MODEL rankine_toluene REFINES rankine_common;
747 cd.component :== 'toluene';
748 METHODS
749 METHOD on_load;
750 RUN ClearAll;
751 RUN default_self;
752 FIX BO.eta; BO.eta := 1.0;
753 FIX TU.eta; TU.eta := 0.85;
754 FIX PU.eta; PU.eta := 0.8;
755 FIX Wdot; Wdot := 100 {MW};
756 FIX CO.outlet.T; CO.outlet.T := 40 {K} + 273.15 {K};
757 FIX CO.outlet.x; CO.outlet.x := 1e-6;
758 FIX PU.outlet.p; PU.outlet.p := 150 {bar};
759 FIX BO.outlet.T; BO.outlet.T := 580 {K} + 273.15 {K};
760
761 SOLVER QRSlv;
762 OPTION convopt 'RELNOM_SCALE';
763 OPTION iterationlimit 200;
764
765 FREE CO.outlet.h;
766 FIX CO.outlet.x; CO.outlet.x := 1e-6;
767
768 END on_load;
769 METHOD default_self;
770 RUN rankine_common::default_self;
771 PU.inlet.h := 400 {kJ/kg};
772 BO.outlet.h := 400 {kJ/kg};
773 CO.outlet.h := 400 {kJ/kg};
774 CO.outlet.p := 10 {kPa};
775 END default_self;
776 END rankine_toluene;
777
778
779
780 MODEL rankine_ammonia REFINES rankine_common;
781 cd.component :== 'ammonia';
782 METHODS
783 METHOD on_load;
784 RUN ClearAll;
785 RUN default_self;
786 FIX BO.eta; BO.eta := 1.0;
787 FIX TU.eta; TU.eta := 0.85;
788 FIX PU.eta; PU.eta := 0.8;
789 FIX Wdot; Wdot := 100 {MW};
790 FIX CO.outlet.T; CO.outlet.T := 40 {K} + 273.15 {K};
791 FIX CO.outlet.x; CO.outlet.x := 1e-6;
792 FIX PU.outlet.p; PU.outlet.p := 150 {bar};
793 FIX BO.outlet.T; BO.outlet.T := 580 {K} + 273.15 {K};
794
795 SOLVER QRSlv;
796 OPTION convopt 'RELNOM_SCALE';
797 OPTION iterationlimit 200;
798
799 FREE CO.outlet.h;
800 FIX CO.outlet.x; CO.outlet.x := 1e-6;
801
802 END on_load;
803 METHOD default_self;
804 RUN rankine_common::default_self;
805 PU.inlet.h := 400 {kJ/kg};
806 BO.outlet.h := 400 {kJ/kg};
807 CO.outlet.h := 400 {kJ/kg};
808 CO.outlet.p := 10 {kPa};
809 END default_self;
810 END rankine_ammonia;
811
812
813
814 (*------------------------------------------------------------------------------
815 REHEAT RANKINE CYCLE
816 *)
817 MODEL rankine_reheat_common;
818 BO1 IS_A boiler_simple;
819 BO2 IS_A boiler_simple;
820 TU1 IS_A turbine_simple;
821 TU2 IS_A turbine_simple;
822 CO IS_A condenser_simple;
823 PU IS_A pump_simple;
824
825 BO1.outlet, TU1.inlet ARE_THE_SAME;
826 TU1.outlet, BO2.inlet ARE_THE_SAME;
827 BO2.outlet, TU2.inlet ARE_THE_SAME;
828 TU2.outlet, CO.inlet ARE_THE_SAME;
829 CO.outlet, PU.inlet ARE_THE_SAME;
830 PU.outlet, BO1.inlet ARE_THE_SAME;
831
832 BO1.eta, BO2.eta ARE_THE_SAME;
833
834 (* boiler peak temperature is reached for both main and reheat... *)
835 BO1.outlet.T, BO2.outlet.T ARE_THE_SAME;
836
837 mdot ALIASES PU.mdot;
838
839 T_H ALIASES BO1.outlet.T;
840 T_C ALIASES CO.outlet.T;
841
842 eta IS_A fraction;
843 eta * (BO1.Qdot_fuel + BO2.Qdot_fuel) = TU1.Wdot + TU2.Wdot + PU.Wdot;
844
845 DE_cycle IS_A energy_rate;
846 DE_cycle = BO1.Qdot + BO2.Qdot + CO.Qdot - TU1.Wdot - TU2.Wdot - PU.Wdot;
847
848 eta_carnot IS_A fraction;
849 eta_carnot = 1 - T_C / T_H;
850 METHODS
851 METHOD default_self;
852 RUN BO1.default_self;
853 RUN BO2.default_self;
854 RUN TU1.default_self;
855 RUN TU2.default_self;
856 RUN CO.default_self;
857 RUN PU.default_self;
858 END default_self;
859 END rankine_reheat_common;
860
861 (*
862 A model for Rankine cycle with water as the working fluid
863 *)
864 MODEL rankine_reheat_water REFINES rankine_reheat_common;
865 BO1.cd.component :== 'water';
866 METHODS
867 METHOD on_load;
868 RUN default_self;
869 RUN cengel_ex_10_4;
870 END on_load;
871 METHOD cengel_ex_10_4;
872 (* This example 10.4 from Cengel & Boles, 2011, 'Thermodynamics: An
873 Engineering Approach', 7th Ed., McGraw-Hill. *)
874 RUN ClearAll;
875 RUN default_self;
876 FIX BO1.eta; BO1.eta := 1.0;
877 FIX TU1.eta; TU1.eta := 1.0;
878 FIX TU2.eta; TU2.eta := 1.0;
879 FIX PU.eta; PU.eta := 1.0;
880
881 FIX TU1.inlet.p; TU1.inlet.p := 15 {MPa};
882 FIX TU1.inlet.T; TU1.inlet.T := (600 {K} + 273.15 {K});
883 FIX BO2.outlet.T; BO2.outlet.T := TU1.inlet.T;
884 FIX TU2.outlet.x; TU2.outlet.x := 0.896;
885 FIX CO.inlet.p; CO.inlet.p := 10 {kPa};
886 FIX CO.outlet.x; CO.outlet.x := 1e-6;
887 FIX mdot; mdot := 1 {kg/s};
888 END cengel_ex_10_4;
889 METHOD self_test_cengel;
890 ASSERT abs(TU2.outlet.s -7.3688 {kJ/kg/K}) < 0.0001 {kJ/kg/K};
891 ASSERT abs(TU2.outlet.h - 2335.1 {kJ/kg}) < 0.1 {kJ/kg};
892 ASSERT abs(BO2.outlet.p - 4.0 {MPa}) < 0.05 {MPa};
893 ASSERT abs(BO2.outlet.h - 3674.9 {kJ/kg}) < 0.2 {kJ/kg};
894 ASSERT abs(eta - 0.450) < 0.0005;
895 END self_test_cengel;
896 METHOD default_self;
897 RUN rankine_reheat_common::default_self;
898 BO1.outlet.h := 3000 {kJ/kg}; (* guess *)
899 TU1.outlet.h := 3000 {kJ/kg}; (* guess *)
900 TU2.inlet.h := 3000 {kJ/kg}; (* guess *)
901 END default_self;
902 END rankine_reheat_water;

john.pye@anu.edu.au
ViewVC Help
Powered by ViewVC 1.1.22