MATLAB: How to find the roots of a symbolic polynimial

coefficientsdegreedoublefunctioninversematrixpolynomialrootssymbolictransfer

I create a symbolic transfer function matrix. I find its inverse. The first element of the matrix is a polynomial. Note that this polynomial is symbolic so no operation can be done on it. I want to convert this to a polynomial and find the roots. How should I go about this? Thanks.
aa =
– 30*s^4 + 300*s^3
>> coeffs(aa)
ans =
[ 300, -30]
Here aa is the polynomial I go ahead and extract the coefficients and then i can do a "aa=double(aa)" to convert it to double. And then find the roots. But the problem is When I do the coeffs(aa) i should get [-30 300 0 0] and not [300 -30]. Even if I get [0 0 300 -30], I can get my way through. But the issue is i need those missing zeros (coefficients of s^2 and s^1).
Thanks,

Best Answer

No. It simply is not true that NO operation can be done on that polynomial.
syms s
p = -30*s^4 + 300*s^3;
solve( p )
ans =
0
0
0
10
vpasolve( p )
ans =
0
0
0
10.0
Both of those tools operate directly on symbolic polynomials. Yes, I could also have converted it into a polymonial as a vector of coefficients, then used roots. But that may, for some polynomials, be more prone to numerical error.
roots(sym2poly(p))
ans =
0
0
0
10
For an extreme case of why the roots path may be less than the best solution, try this:
p = expand((s-1)^15)
p =
s^15 - 15*s^14 + 105*s^13 - 455*s^12 + 1365*s^11 - 3003*s^10 + 5005*s^9 - 6435*s^8 + 6435*s^7 - 5005*s^6 + 3003*s^5 - 1365*s^4 + 455*s^3 - 105*s^2 + 15*s - 1
roots(sym2poly(p))
ans =
1.209 + 0i
1.1857 + 0.091966i
1.1857 - 0.091966i
1.1237 + 0.15986i
1.1237 - 0.15986i
1.0424 + 0.19023i
1.0424 - 0.19023i
0.96223 + 0.18319i
0.96223 - 0.18319i
0.89706 + 0.14756i
0.89706 - 0.14756i
0.85307 + 0.094232i
0.85307 - 0.094232i
0.8314 + 0.032225i
0.8314 - 0.032225i
solve(p)
ans =
1
1
1
1
1
1
1
1
1
1
1
1
1
1
1
vpasolve(p)
ans =
1.0
1.0
1.0
1.0
1.0
1.0
1.0
1.0
1.0
1.0
1.0
1.0
1.0
1.0
1.0
As you can see, both solve and vpasolve had no problems, while roots was a bit less accurate. Admittedly, this is a nasty test case for roots. Of course I chose that test case because I knew roots would have a hard time with a problem with many multiple roots.
So had I given a different test case
syms s
p = expand(prod(s - (1:15)))
p =
s^15 - 120*s^14 + 6580*s^13 - 218400*s^12 + 4899622*s^11 - 78558480*s^10 + 928095740*s^9 - 8207628000*s^8 + 54631129553*s^7 - 272803210680*s^6 + 1009672107080*s^5 - 2706813345600*s^4 + 5056995703824*s^3 - 6165817614720*s^2 + 4339163001600*s - 1307674368000
roots(sym2poly(p))
ans =
15
14
13
12
11
10
9
8
7
6
5
4
3
2
1
Here roots worked very well. In fact, understanding how roots works can help you to know why this case worked well with roots and the first fails. The problem is, you don't always know when you will find something that will be problematic. So if you are starting with a symbolic polynomial, then it would in general be best to use a tool designed for that if you can do so. So, lets see what happens here...
roots(sym2poly(p-1))
ans =
15
14
13
12
11
10
9
8
7
6
5
4
3
2
1
Oops. Subtracting 1 from p should have shifted the roots by just a tiny amount. vpasolve does a lot better.
vpasolve(p-1)
ans =
1.0000000000114707455981575587965
1.9999999998394095616880079532128
3.0000000010438378511402592310782
3.9999999958246486231120653234589
5.0000000114822164548170589408461
5.9999999770355676010939194536657
7.0000000344466493478141158541341
7.9999999606324011085914925439765
9.0000000344466487121507429640661
9.9999999770355670255962156025775
11.000000011482216231837857685089
11.999999995824648581740694564924
13.000000001043837847646550678815
13.99999999983940956157555975473
15.000000000011470745597301890631