Solving equation with for loop is slow

2 views (last 30 days)
I have an equation (5th order Polynomial) and I have to solve it every time for different variables A,B and Coeff as written down. And the coefficient are quite alot (100000) I had no other way than using the for loop to do it but it is incredibely slow. Could anyone please give me a suggestion to make it faster or if there is another way to solve the equation faster.
This is my code:
tCounter = zeros(length(A),1);
for i = 1:length(A)
syms t
Check = (isnan(B(i,1))==1);
if Check ==1
tCounter(i) = NaN;
else
Equation = -(Coeff(21).*((B(i,2) + t*A(i,2)).^5) + (Coeff(20).*((B(i,2) + t*A(i,2)).^4)).*(B(i,1) + t*A(i,1)) + Coeff(19).*((B(i,2) + t*A(i,2)).^4) + (Coeff(18).*((B(i,2) + t*A(i,2)).^3)).*((B(i,1) + t*A(i,1)).^2) + (Coeff(17).*((B(i,2) + t*A(i,2)).^3)).*(B(i,1) + t*A(i,1)) + Coeff(16).*((B(i,2) + t*A(i,2)).^3) + (Coeff(15).*((B(i,2) + t*A(i,2)).^2)).*((B(i,1) + t*A(i,1)).^3) + (Coeff(14).*((B(i,2) + t*A(i,2)).^2)).*((B(i,1) + t*A(i,1)).^2) + (Coeff(13).*((B(i,2) + t*A(i,2)).^2)).*(B(i,1) + t*A(i,1)) + Coeff(12).*((B(i,2) + t*A(i,2)).^2) + (Coeff(11).*((B(i,2) + t*A(i,2)))).*((B(i,1) + t*A(i,1)).^4) + (Coeff(10).*(B(i,2) + t*A(i,2))).*((B(i,1) + t*A(i,1)).^3) + (Coeff(9).*(B(i,2) + t*A(i,2))).*((B(i,1) + t*A(i,1)).^2) + (Coeff(8).*(B(i,2) + t*A(i,2))).*((B(i,1) + t*A(i,1))) + (Coeff(7).*(B(i,2) + t*A(i,2))) + Coeff(6).*((B(i,1) + t*A(i,1)).^5) + Coeff(5).*((B(i,1) + t*A(i,1)).^4) + Coeff(4).*((B(i,1) + t*A(i,1)).^3) + Coeff(3).*((B(i,1) + t*A(i,1)).^2) + Coeff(2).*(B(i,1) + t*A(i,1)) + Coeff(1)) + Thickness - (B(i,3) + t*A(i,3));
t = solve(Equation,t);
t = double (t);
t(imag(t) ~= 0) = [];
t(t<0) = [];
t = min(t);
tCounter(i) = t;
end
end
Many thanks in advance

Accepted Answer

Walter Roberson
Walter Roberson on 14 Oct 2013
solve() generically outside of the loop and then subs() or matlabFunction() to get code executed for each loop instance.
t = roots( [Coeff(6)*A(i, 1)^5+Coeff(11)*A(i, 1)^4*A(i, 2)+Coeff(15)*A(i, 1)^3*A(i, 2)^2+Coeff(18)*A(i, 1)^2*A(i, 2)^3+Coeff(20)*A(i, 1)*A(i, 2)^4+Coeff(21)*A(i, 2)^5,
(5*Coeff(6)*B(i, 1)+Coeff(11)*B(i, 2)+Coeff(5))*A(i, 1)^4+(2*(2*Coeff(11)*B(i, 1)+Coeff(15)*B(i, 2)+(1/2)*Coeff(10)))*A(i, 1)^3*A(i, 2)+(3*Coeff(15)*B(i, 1)+3*Coeff(18)*B(i, 2)+Coeff(14))*A(i, 1)^2*A(i, 2)^2+(2*Coeff(18)*B(i, 1)+4*Coeff(20)*B(i, 2)+Coeff(17))*A(i, 1)*A(i, 2)^3+(Coeff(20)*B(i, 1)+5*Coeff(21)*B(i, 2)+Coeff(19))*A(i, 2)^4,
(10*Coeff(6)*B(i, 1)^2+Coeff(15)*B(i, 2)^2+(4*Coeff(11)*B(i, 2)+4*Coeff(5))*B(i, 1)+Coeff(10)*B(i, 2)+Coeff(4))*A(i, 1)^3+(3*(2*Coeff(11)*B(i, 1)^2+Coeff(18)*B(i, 2)^2+(2*Coeff(15)*B(i, 2)+Coeff(10))*B(i, 1)+(2/3)*Coeff(14)*B(i, 2)+(1/3)*Coeff(9)))*A(i, 1)^2*A(i, 2)+(3*Coeff(15)*B(i, 1)^2+6*Coeff(20)*B(i, 2)^2+(6*Coeff(18)*B(i, 2)+2*Coeff(14))*B(i, 1)+3*Coeff(17)*B(i, 2)+Coeff(13))*A(i, 1)*A(i, 2)^2+(Coeff(18)*B(i, 1)^2+10*Coeff(21)*B(i, 2)^2+(4*Coeff(20)*B(i, 2)+Coeff(17))*B(i, 1)+4*Coeff(19)*B(i, 2)+Coeff(16))*A(i, 2)^3,
(10*Coeff(6)*B(i, 1)^3+Coeff(18)*B(i, 2)^3+(6*Coeff(11)*B(i, 2)+6*Coeff(5))*B(i, 1)^2+Coeff(14)*B(i, 2)^2+(3*Coeff(15)*B(i, 2)^2+3*Coeff(10)*B(i, 2)+3*Coeff(4))*B(i, 1)+Coeff(9)*B(i, 2)+Coeff(3))*A(i, 1)^2+(4*Coeff(11)*B(i, 1)^3+4*Coeff(20)*B(i, 2)^3+(6*Coeff(15)*B(i, 2)+3*Coeff(10))*B(i, 1)^2+3*Coeff(17)*B(i, 2)^2+(6*Coeff(18)*B(i, 2)^2+4*Coeff(14)*B(i, 2)+2*Coeff(9))*B(i, 1)+2*Coeff(13)*B(i, 2)+Coeff(8))*A(i, 1)*A(i, 2)+(Coeff(15)*B(i, 1)^3+10*Coeff(21)*B(i, 2)^3+(3*Coeff(18)*B(i, 2)+Coeff(14))*B(i, 1)^2+6*Coeff(19)*B(i, 2)^2+(6*Coeff(20)*B(i, 2)^2+3*Coeff(17)*B(i, 2)+Coeff(13))*B(i, 1)+3*Coeff(16)*B(i, 2)+Coeff(12))*A(i, 2)^2,
(5*Coeff(6)*A(i, 1)+Coeff(11)*A(i, 2))*B(i, 1)^4+(Coeff(20)*A(i, 1)+5*Coeff(21)*A(i, 2))*B(i, 2)^4+(4*Coeff(5)*A(i, 1)+Coeff(10)*A(i, 2)+(4*Coeff(11)*A(i, 1)+2*Coeff(15)*A(i, 2))*B(i, 2))*B(i, 1)^3+(Coeff(17)*A(i, 1)+4*Coeff(19)*A(i, 2))*B(i, 2)^3+((3*Coeff(15)*A(i, 1)+3*Coeff(18)*A(i, 2))*B(i, 2)^2+3*Coeff(4)*A(i, 1)+Coeff(9)*A(i, 2)+(3*Coeff(10)*A(i, 1)+2*Coeff(14)*A(i, 2))*B(i, 2))*B(i, 1)^2+(Coeff(13)*A(i, 1)+3*Coeff(16)*A(i, 2))*B(i, 2)^2+Coeff(2)*A(i, 1)+Coeff(7)*A(i, 2)+A(i, 3)+((2*Coeff(18)*A(i, 1)+4*Coeff(20)*A(i, 2))*B(i, 2)^3+(2*Coeff(14)*A(i, 1)+3*Coeff(17)*A(i, 2))*B(i, 2)^2+2*Coeff(3)*A(i, 1)+Coeff(8)*A(i, 2)+(2*Coeff(9)*A(i, 1)+2*Coeff(13)*A(i, 2))*B(i, 2))*B(i, 1)+(Coeff(8)*A(i, 1)+2*Coeff(12)*A(i, 2))*B(i, 2),
Coeff(6)*B(i, 1)^5+Coeff(21)*B(i, 2)^5+(Coeff(11)*B(i, 2)+Coeff(5))*B(i, 1)^4+Coeff(19)*B(i, 2)^4+(Coeff(15)*B(i, 2)^2+Coeff(10)*B(i, 2)+Coeff(4))*B(i, 1)^3+Coeff(16)*B(i, 2)^3+(Coeff(18)*B(i, 2)^3+Coeff(14)*B(i, 2)^2+Coeff(9)*B(i, 2)+Coeff(3))*B(i, 1)^2+Coeff(12)*B(i, 2)^2-Thickness+(Coeff(20)*B(i, 2)^4+Coeff(17)*B(i, 2)^3+Coeff(13)*B(i, 2)^2+Coeff(8)*B(i, 2)+Coeff(2))*B(i, 1)+Coeff(7)*B(i, 2)+B(i, 3)+Coeff(1) ] );
and then do the filtering like you had before.
  4 Comments
Walter Roberson
Walter Roberson on 14 Oct 2013
I solve()'d in Maple. You could do the equivalent using
syms A B i t
Equation = -(Coeff(21).*((B(i,2) + t*A(i,2)).^5) + (Coeff(20).*((B(i,2) + t*A(i,2)).^4)).*(B(i,1) + t*A(i,1)) + Coeff(19).*((B(i,2) + t*A(i,2)).^4) + (Coeff(18).*((B(i,2) + t*A(i,2)).^3)).*((B(i,1) + t*A(i,1)).^2) + (Coeff(17).*((B(i,2) + t*A(i,2)).^3)).*(B(i,1) + t*A(i,1)) + Coeff(16).*((B(i,2) + t*A(i,2)).^3) + (Coeff(15).*((B(i,2) + t*A(i,2)).^2)).*((B(i,1) + t*A(i,1)).^3) + (Coeff(14).*((B(i,2) + t*A(i,2)).^2)).*((B(i,1) + t*A(i,1)).^2) + (Coeff(13).*((B(i,2) + t*A(i,2)).^2)).*(B(i,1) + t*A(i,1)) + Coeff(12).*((B(i,2) + t*A(i,2)).^2) + (Coeff(11).*((B(i,2) + t*A(i,2)))).*((B(i,1) + t*A(i,1)).^4) + (Coeff(10).*(B(i,2) + t*A(i,2))).*((B(i,1) + t*A(i,1)).^3) + (Coeff(9).*(B(i,2) + t*A(i,2))).*((B(i,1) + t*A(i,1)).^2) + (Coeff(8).*(B(i,2) + t*A(i,2))).*((B(i,1) + t*A(i,1))) + (Coeff(7).*(B(i,2) + t*A(i,2))) + Coeff(6).*((B(i,1) + t*A(i,1)).^5) + Coeff(5).*((B(i,1) + t*A(i,1)).^4) + Coeff(4).*((B(i,1) + t*A(i,1)).^3) + Coeff(3).*((B(i,1) + t*A(i,1)).^2) + Coeff(2).*(B(i,1) + t*A(i,1)) + Coeff(1)) + Thickness - (B(i,3) + t*A(i,3));
tsym = solve(simplify(Equation), t);
tfun = matlabFunction(tsym, 'vars', {'A', 'B', 'i'});
then
for i = 1:length(realA)
if isnan(B(i,1))
tCounter(i) = NaN;
else
t = tfun(realA, realB, i);
t(imag(t) ~= 0) = [];
t(t<0) = [];
t = min(t);
tCounter(i) = t;
end
end
The "for" loop is still there, but the solve() has been done only once, and then each iteration of the loop the anonymous function equivalent of the solution is used, passing in appropriate parameters.
Jack_111
Jack_111 on 14 Oct 2013
It was more than perfect
Big thanks

Sign in to comment.

More Answers (1)

guy tau
guy tau on 23 Feb 2023
Hi @Wlater, a very late replay, buy unfortentaly, i'm currently dealing with a simialr issue, and hopfully you can assisit me as well.
I have large table of data (~30000 rows), in which I use the solver function on some of the varibles from the table to predect and compare to a known sampled varible.
I tried your suggested code, wrtiren as:
syms a.var1 a.var2 a.var3 a.var4 i X
Equation = ((a.var1(i) -c1*(X)^4)- (c2*a.var2(i)*(6.105.*exp((c3*X)./(x+c4)) -a.var3(i))) - (c5*(x-a.var4(i)))) = 0;
tsym = solve(simplify(Equation), X);
tfun = matlabFunction(tsym, 'vars', {'a.var1', 'a.var2', 'a.var3', 'a.var4','i'});
for i = 1:height(a)
t(i) = tfun(a.var1,a.var2,a.var3,a.var4, i);
end
where
c1,c2,c3,c4 and c5 are constants
and a.var1 to a.var 4 are the varibiles from the table
Unfortunately I got the follwing error back
Error using sym/subsindex
Invalid indexing or function definition. Indexing must follow MATLAB indexing. Function arguments must be symbolic variables, and function body must be sym expression.
Error in indexing (line 1075)
R_tilde = builtin('subsref',L_tilde,Idx);
Related documentation
I assume the problem is realted to the index table, but i'm struggling the find the solution
If other solution pop's to your mind that will be great as well.
currently, letting the loop run by just using solver is just to slow...

Tags

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!