1 ## Copyright (C) 2011 Lukas F. Reichlin
3 ## This file is part of LTI Syncope.
5 ## LTI Syncope is free software: you can redistribute it and/or modify
6 ## it under the terms of the GNU General Public License as published by
7 ## the Free Software Foundation, either version 3 of the License, or
8 ## (at your option) any later version.
10 ## LTI Syncope is distributed in the hope that it will be useful,
11 ## but WITHOUT ANY WARRANTY; without even the implied warranty of
12 ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 ## GNU General Public License for more details.
15 ## You should have received a copy of the GNU General Public License
16 ## along with LTI Syncope. If not, see <http://www.gnu.org/licenses/>.
19 ## @deftypefn{Function File} {[@var{Gr}, @var{info}] =} __modred_ab09id__ (@var{method}, @dots{})
20 ## Backend for btamodred and spamodred.
23 ## Author: Lukas Reichlin <lukas.reichlin@gmail.com>
24 ## Created: November 2011
27 function [Gr, info] = __modred_ab09id__ (method, varargin)
33 if (method != "bta" && method != "spa")
34 error ("modred: invalid method");
38 varargin = varargin(2:end);
41 error ("%smodred: first argument must be an LTI system", method);
44 if (nargin > 2) # *modred (G, ...)
45 if (is_real_scalar (varargin{1})) # *modred (G, nr)
46 varargin = horzcat (varargin(2:end), {"order"}, varargin(1));
48 if (isstruct (varargin{1})) # *modred (G, opt, ...), *modred (G, nr, opt, ...)
49 varargin = horzcat (__opt2cell__ (varargin{1}), varargin(2:end));
51 ## order placed at the end such that nr from *modred (G, nr, ...)
52 ## and *modred (G, nr, opt, ...) overrides possible nr's from
53 ## key/value-pairs and inside opt struct (later keys override former keys,
54 ## nr > key/value > opt)
57 nkv = numel (varargin); # number of keys and values
60 error ("%smodred: keys and values must come in pairs", method);
63 [a, b, c, d, tsam, scaled] = ssdata (G);
68 alpha = __modred_default_alpha__ (dt);
69 av = bv = cv = dv = [];
71 aw = bw = cw = dw = [];
73 alphac = alphao = 0.0;
77 bf = true; # balancing-free
83 ## handle keys and values
85 key = lower (varargin{k});
88 case {"left", "output", "v"}
89 [av, bv, cv, dv, jobv] = __modred_check_weight__ (val, dt, p, []);
91 case {"right", "input", "w"}
92 [aw, bw, cw, dw, jobw] = __modred_check_weight__ (val, dt, [], m);
94 case {"order", "n", "nr"}
95 [nr, ordsel] = __modred_check_order__ (val, rows (a));
98 tol1 = __modred_check_tol__ (val, "tol1");
101 tol2 = __modred_check_tol__ (val, "tol2");
104 alpha = __modred_check_alpha__ (val, dt);
107 switch (tolower (val))
113 error ("modred: '%s' is an invalid approach", val);
116 case {"jobc", "gram-ctrb"}
117 jobc = __modred_check_gram__ (val, "gram-ctrb");
119 case {"jobo", "gram-obsv"}
120 jobo = __modred_check_gram__ (val, "gram-obsv");
122 case {"alphac", "alpha-ctrb"}
123 alphac = __modred_check_alpha_gram__ (val, "alpha-ctrb");
125 case {"alphao", "alpha-obsv"}
126 alphao = __modred_check_alpha_gram__ (val, "alpha-obsv");
128 case {"equil", "equilibrate", "equilibration", "scale", "scaling"}
129 scaled = __modred_check_equil__ (val);
132 warning ("%smodred: invalid property name '%s' ignored", method, key);
136 ## handle type of frequency weighting
138 weight = 3; # 'B': both left and right weightings V and W are used
140 weight = 1; # 'L': only left weighting V is used (W = I)
142 weight = 2; # 'R': only right weighting W is used (V = I)
144 weight = 0; # 'N': no weightings are used (V = I, W = I)
147 ## handle model reduction approach
148 if (method == "bta" && ! bf) # 'B': use the square-root Balance & Truncate method
150 elseif (method == "bta" && bf) # 'F': use the balancing-free square-root Balance & Truncate method
152 elseif (method == "spa" && ! bf) # 'S': use the square-root Singular Perturbation Approximation method
154 elseif (method == "spa" && bf) # 'P': use the balancing-free square-root Singular Perturbation Approximation method
157 error ("modred: invalid job option"); # this should never happen
161 ## perform model order reduction
162 [ar, br, cr, dr, nr, hsv, ns] = slab09id (a, b, c, d, dt, equil, nr, ordsel, alpha, job, \
165 weight, jobc, jobo, alphac, alphao, \
168 ## assemble reduced order model
169 Gr = ss (ar, br, cr, dr, tsam);
171 ## assemble info struct
172 info = struct ("nr", nr, "ns", ns, "hsv", hsv);