1## Copyright (C) 2009-2016   Lukas F. Reichlin
2##
3## This file is part of LTI Syncope.
4##
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.
9##
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.
14##
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/>.
17
18## -*- texinfo -*-
19## @deftypefn {Function File} {@var{p} =} pole (@var{sys})
20## Compute poles of @acronym{LTI} system.
21##
22## @strong{Inputs}
23## @table @var
24## @item sys
25## @acronym{LTI} model.
26## @end table
27##
28## @strong{Outputs}
29## @table @var
30## @item p
31## Poles of @var{sys}.
32## @end table
33##
34## @strong{Algorithm}@*
35## For (descriptor) state-space models and system/state matrices, @command{pole}
36## relies on Octave's @command{eig}.
37## For @acronym{SISO} transfer functions, @command{pole}
38## uses Octave's @command{roots}.
39## @acronym{MIMO} transfer functions are converted to
40## a @emph{minimal} state-space representation for the
41## computation of the poles.
42##
43## @end deftypefn
44
45## Author: Lukas Reichlin <lukas.reichlin@gmail.com>
46## Contributor: Mark Bronsfeld <m.brnsfld@googlemail.com>
47## Created: October 2009
48## Version: 0.2
49
50function pol = pole (sys)
51
52   if(nargin == 1) # pole(sys)
53     if(!(isa(sys, "lti")) && issquare(sys))
54       pol = eig(sys);
55     elseif(isa(sys, "lti"))
56       pol = __pole__(sys);
57     else
58       error("pole: argument must be an LTI system");
59     endif
60   else
61     print_usage();
62   endif
63
64endfunction
65
66
67%!shared pol_exp, pol_obs
68%! A = [-1, 0,  0;
69%!          0,  -2, 0;
70%!          0,  0,  -3];
71%! pol_exp = [-3;
72%!                   -2;
73%!                   -1];
74%! pol_obs = pole (ss (A, ones (3, 1)));
75%!
76%!assert(pol_obs, pol_exp, 0);
77
78## Poles of descriptor state-space model
79%!shared pol, pol_exp, infp, kronr, kronl, infp_exp, kronr_exp, kronl_exp
80%! A = [  1     0     0     0     0     0     0     0     0
81%!        0     1     0     0     0     0     0     0     0
82%!        0     0     1     0     0     0     0     0     0
83%!        0     0     0     1     0     0     0     0     0
84%!        0     0     0     0     1     0     0     0     0
85%!        0     0     0     0     0     1     0     0     0
86%!        0     0     0     0     0     0     1     0     0
87%!        0     0     0     0     0     0     0     1     0
88%!        0     0     0     0     0     0     0     0     1 ];
89%!
90%! E = [  0     0     0     0     0     0     0     0     0
91%!        1     0     0     0     0     0     0     0     0
92%!        0     1     0     0     0     0     0     0     0
93%!        0     0     0     0     0     0     0     0     0
94%!        0     0     0     1     0     0     0     0     0
95%!        0     0     0     0     1     0     0     0     0
96%!        0     0     0     0     0     0     0     0     0
97%!        0     0     0     0     0     0     1     0     0
98%!        0     0     0     0     0     0     0     1     0 ];
99%!
100%! B = [ -1     0     0
101%!        0     0     0
102%!        0     0     0
103%!        0    -1     0
104%!        0     0     0
105%!        0     0     0
106%!        0     0    -1
107%!        0     0     0
108%!        0     0     0 ];
109%!
110%! C = [  0     1     1     0     3     4     0     0     2
111%!        0     1     0     0     4     0     0     2     0
112%!        0     0     1     0    -1     4     0    -2     2 ];
113%!
114%! D = [  1     2    -2
115%!        0    -1    -2
116%!        0     0     0 ];
117%!
118%! sys = dss (A, B, C, D, E, "scaled", true);
119%! [pol, ~, infp, kronr, kronl] = __sl_ag08bd__ (A, E, [], [], [], true);
120%!
121%! pol_exp = zeros (0,1);
122%!
123%! infp_exp = [0, 3];
124%! kronr_exp = zeros (1,0);
125%! kronl_exp = zeros (1,0);
126%!
127%!assert (pol, pol_exp, 1e-4);
128%!assert (infp, infp_exp);
129%!assert (kronr, kronr_exp);
130%!assert (kronl, kronl_exp);
131