How to fill a variable with the results of an if...elseif statement
조회 수: 2 (최근 30일)
이전 댓글 표시
I am trying to apply the second derivative test to a function and find all the relative maxima, minima, saddlepoints, and inconclusive results from the function's critical points. I think I have my code where I want it, but my fmin, fmax, and saddlePts should have more than just one point (x,y) stored. I'm quite sure that each time a condition is met in the if...elseif statement, that the previous point store is getting overwritten, which results in just last indice to meet the criteria being stored.
How can I get all the 9 points to be stored properly in the if...elseif statement? I.e. How to a prevent the overwriting, and allow fmin, fmax, and saddlePts to be filled with more than one point?
% Using MATLAB, find and evaluate all maxima, minima, and saddle points of
% the function f(x,y)= x*y*(x^2+y^2-2.56).
clear
clc
syms x y % Initiate SYMBOLIC MATH
% Find fist-order partial derivative: fx and fy.
f(x,y)= x*y*(x^2+y^2-2.56);
fx = simplify(diff(f,x)); fy = simplify(diff(f,y));
% Set fx and fy equal to zero and solve for critical points. Save x and y
% values as xcrit and ycrit.
S = solve(fx,fy);
xcrit = S.x; ycrit = S.y;
% Find second-order partial derivatives: fxx, fyy, and fxy.
fxx = simplify(diff(fx,x));
fyy = simplify(diff(fy,y));
fxy = simplify(diff(fx,y));
% Perform a second-order derivative test of each critical point. Label and
% store all maximum, minimum, and saddle points based on criteria:
% If D>0 and fxx(Xc,Yc)>0, then f has a relative minimum at (Xc,Yc).
% If D>0 and fxx(Xc,Yc)>0, then f has a relative maximum at (Xc,Yc).
% If D<0, then f has a saddle point at (Xc,Yc).
% If D=0, then the test is inconclusive.
% Minimums are store as fmin, maximums as fmax, saddle points as saddlePts,
% and inconclusives as inconcl.
Xc = double(xcrit); Yc = double(ycrit);
for ind = 1:9
D=fxx(Xc(ind),Yc(ind))*fyy(Xc(ind),Yc(ind)) - (fxy(Xc(ind),Yc(ind)))^2;
if D > 0 && fxx(Xc(ind),Yc(ind)) > 0
fmin = [Xc(ind) Yc(ind)];
elseif (D > 0) && (fxx(Xc(ind),Yc(ind)) < 0)
fmax = [Xc(ind) Yc(ind)];
elseif (D < 0)
saddlePts = [Xc(ind) Yc(ind)];
elseif (D == 0)
inconcl = [Xc(ind) Yc(ind)];
end
end
% Print relative minimums and maximums, saddle points, and inconclusives.
L = exist('fmin'); K = exist('fmax'); H = exist('saddlePts');
G = exist('inconcl');
fprintf('f(x,y) = %s\n\n', simplify(f));
disp('f has a relative minimum at the following points:');
if (L ~= 0)
disp(array2table(fmin, 'VariableNames', {'x', 'y'})); disp(' ');
else
disp('None'); disp(' ');
end
disp('f has a relative maximum at the following points:');
if (K ~= 0)
disp(array2table(fmax, 'VariableNames', {'x', 'y'})); disp(' ');
else
disp('None'); disp(' ');
end
disp('f has a saddle point at the following points:');
if (H~=0)
disp(array2table(saddlePts, 'VariableNames', {'x', 'y'})); disp(' ');
else
disp('None'); disp(' ');
end
disp('The 2nd derivative test was inconclusive for the following points:');
if (G ~=0)
disp(array2table(inconcl, 'VariableNames', {'x', 'y'})); disp(' ');
else
disp('None');
end
댓글 수: 0
채택된 답변
Torsten
2024년 10월 1일
편집: Torsten
2024년 10월 1일
Use
imin = 0;
imax = 0;
isaddlePts = 0;
iinconcl = 0;
for ind = 1:9
D=fxx(Xc(ind),Yc(ind))*fyy(Xc(ind),Yc(ind)) - (fxy(Xc(ind),Yc(ind)))^2;
if D > 0 && fxx(Xc(ind),Yc(ind)) > 0
imin = imin + 1;
fmin(imin,:) = [Xc(ind) Yc(ind)];
elseif (D > 0) && (fxx(Xc(ind),Yc(ind)) < 0)
imax = imax + 1;
fmax(imax,:) = [Xc(ind) Yc(ind)];
elseif (D < 0)
isaddlePts = isaddlePts + 1;
saddlePts(isaddlePts,:) = [Xc(ind) Yc(ind)];
elseif (D == 0)
iinconcl = iinconcl + 1;
inconcl(iinconcl,:) = [Xc(ind) Yc(ind)];
end
end
추가 답변 (1개)
Steven Lord
2024년 10월 1일
Rather than creating variables whose number of rows is not known ahead of time, I'd consider creating a table of coordinates and have one or more variables in that table indicating what it is.
% Using MATLAB, find and evaluate all maxima, minima, and saddle points of
% the function f(x,y)= x*y*(x^2+y^2-2.56).
syms x y % Initiate SYMBOLIC MATH
% Find fist-order partial derivative: fx and fy.
f(x,y)= x*y*(x^2+y^2-2.56);
fx = simplify(diff(f,x)); fy = simplify(diff(f,y));
% Set fx and fy equal to zero and solve for critical points. Save x and y
% values as xcrit and ycrit.
S = solve(fx,fy);
xcrit = S.x; ycrit = S.y;
% Find second-order partial derivatives: fxx, fyy, and fxy.
fxx = simplify(diff(fx,x));
fyy = simplify(diff(fy,y));
fxy = simplify(diff(fx,y));
% Perform a second-order derivative test of each critical point. Label and
% store all maximum, minimum, and saddle points based on criteria:
% If D>0 and fxx(Xc,Yc)>0, then f has a relative minimum at (Xc,Yc).
% If D>0 and fxx(Xc,Yc)>0, then f has a relative maximum at (Xc,Yc).
% If D<0, then f has a saddle point at (Xc,Yc).
% If D=0, then the test is inconclusive.
% Minimums are store as fmin, maximums as fmax, saddle points as saddlePts,
% and inconclusives as inconcl.
Xc = double(xcrit); Yc = double(ycrit);
results = table('Size', [numel(Xc), 3], ...
'VariableTypes', ["sym", "sym", "string"], ...
'VariableNames', ["X", "Y", "type"]);
results.X = xcrit(:);
results.Y = ycrit(:);
% generalize the loop to handle case where xcrit/ycrit have different
% numbers of elements, using numel(Xc) instead of hard-coding 9
for ind = 1:numel(Xc)
D=fxx(Xc(ind),Yc(ind))*fyy(Xc(ind),Yc(ind)) - (fxy(Xc(ind),Yc(ind)))^2;
if D > 0 && fxx(Xc(ind),Yc(ind)) > 0
results.type(ind) = "min";
elseif (D > 0) && (fxx(Xc(ind),Yc(ind)) < 0)
results.type(ind) = "max";
elseif (D < 0)
results.type(ind) = "saddle";
elseif (D == 0) % May be able to just use "else" instead of "elseif (D==0)"
results.type(ind) = "inconclusive";
end
end
disp(results)
Then if you needed to do anything with points of a certain type:
minima = results(results.type == "min", :)
You could also have individual variables in the table if you want to have booleans to work with.
results.min = results.type == "min";
results.max = results.type == "max";
results.saddle = results.type == "saddle";
results.inconclusive = results.type == "inconclusive";
disp(results)
댓글 수: 0
참고 항목
카테고리
Help Center 및 File Exchange에서 Calculus에 대해 자세히 알아보기
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!