Is it possible to use 'solve' on a vector of functions?

Is it possible to use 'solve' function on a column/row vector of functions where each row/column is a function of just one variable?
syms t
funcVec = [3*t+2; 5t-3]
solve(funcVec)
For example, running the above lines of code should give me a vector
[-2/3; 3/5].

Answers (1)

No.
You can use
arrayfun(@solve, funcVec)
Or you can use the symbolic map() function. Note that map() is not exposed at the MATLAB level, so you would need evalin() or feval()

8 Comments

Are you sure I can use 'arrayfun'? When I run the above line, I get the following error:
Error using arrayfun
sym output type is not currently implemented.
I do not have the symbolic toolbox to test with.
Try
arrayfun(@solve, funcVec, 'Uniform', 0)
and then cell2mat() the result.
Thanks very much. That does the job.
It would have been nice if 'arrayfun' works with 'subs' also. (This is in reference to my other question which I am sure you looked at - http://www.mathworks.com/matlabcentral/answers/52856-how-can-i-perform-element-wise-substitution-using-subs-without-using-for-loop)
arrayfun( @(A, B, C) solve(subs(A, B, C)), 'Uniform', 0)
Can you please elaborate on how I can use the above statement in the following code to avoid the for loop?
BOX = randi(1000, [240 9]);
boxCOM = zeros(size(BOX,1), 3);
P1 = BOX(:,1:3)/1000;
P2 = BOX(:,4:6)/1000;
P3 = BOX(:,7:9)/1000;
normal = cross(P1 - P2, P1 - P3);
d = dot(-P1, normal,2);
x = 0.1;
d2 = d - x*sqrt(sum(normal.^2, 2));
syms x y z t;
P = [x.*ones(size(BOX,1), 1) y.*ones(size(BOX, 1), 1)... z.*ones(size(BOX,1), 1)];
planefunction2 = ((normal(:,1).*x)+(normal(:,2).*y)+(normal(:,3).*z)-(d2));
line = P1 + t*normal;
for k = 1 : size(BOX,1)
newfunction = subs(planefunction2(k), P(k,:), line(k,:));
t0 = solve(newfunction);
boxCOM(k,:) = double(subs(line(k,:),t,t0));
end
I understand that instead of placing 'solve' inside the loop I can use
arrayfun(@solve, newfunction, 'Uniform', 0)
But, I am not sure how I can use the statement
arrayfun( @(A, B, C) solve(subs(A, B, C)), 'Uniform', 0)
to eliminate the need for 'subs' in the first and third lines of the 'for' loop?
boxCOM = arrayfun( @(k) double(subs(line(k,:), t, solve(subs(planefunction2(k), P(k,:), line(k,:))))), 1:size(BOX,1), 'Uniform', 0);
boxCOM = cell2mat(boxCOM);
If it looks almost like your existing code, it should. arrayfun() has no magic to it: it just implements a "for loop" with a different syntax.
Walter. That's just awesome.
But, you are right. arrayfun() is just another way of writing a 'for' loop. As a matter of fact, arrayfun() saved me only a few milliseconds and nothing more. I think it's better I stop pursuing vector functionality for symbolic math functions like 'subs' and 'solve' as I understand that MATLAB calls altogether a different engine, to solve such problems, which I think doesn't possess the speed.
Yup. You would probably get better speed by evalin(symengine, ...) or feval(symengine, ...) some code that did the work for you all at the MuPAD level, such as by using MuPAD's map() . At the very least that would remove the overhead of talking to the symbolic engine for each operation.

Sign in to comment.

Tags

Asked:

on 6 Nov 2012

Community Treasure Hunt

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

Start Hunting!