How to get real root of a function using fminbnd?

Hello, How can I force MATLAB to only give real solutions to a math function using fminbnd?
This is my code:
x=-1:0.01:8; y=@(x) (x).^(4/3); yinv=@(x) -((x).^(4/3)); x_1=-1; x_2=8;
[xmin, ymin]=fminbnd(y,x_1,x_2);
[xmax, ymax]=fminbnd(yinv,x_1,x_2);
fprintf('The local maximum is %.2f at x = %.2f\n', -ymax, xmax)
fprintf('The local minimum is %.2f at x = %.2f\n', ymin, xmin)
Gives this as output:
The local maximum is 16.00 at x = 8.00 % Good. This is what it's supposed to be based on the x domain
The local minimum is -0.50 at x = -1.00 % This is the problem. (-1)^(4/3)=1 (The real solution)
Also, when I test in the Command Window:
(-1)^(4/3)
I get
-0.5000-0.866i
I think my code is spitting out the real part of (-1)^(4/3) that I get in Command Window.
Thanks for your help

1 Commento

John D'Errico
John D'Errico il 30 Apr 2025
Spostato: John D'Errico il 30 Apr 2025
I think you are confused. FMINBND is a MINIMIZER. It does not compute a root. If the minimum of your objective can be negative, you will get it.
You want to use fzero to compute a root. Even at that, you need to understand that raising a negative number to a fractional power has a complex result as the primary solution.

Accedi per commentare.

 Risposta accettata

It sounds like you want to see the result:
(-1)^(4/3) == 1
To do that, you want to use nthroot, by splitting the fraction in that exponent into two parts.
x^(4/3) = (x^(1/3))^4
And therefore, we would have
f = @(x) nthroot(x,3)^4;
f(-1)
ans = 1
So now a nice real number.
This works as long as the denominator of the exponent is an integer, and thus we can use nthroot. Will it still work, if we tried that trick on x^0.63? Well, in theory, it migh seem so, since 0.63 = 63/100. But nthroot will fail then. Try it:
nthroot(-2,100)^63
Error using nthroot (line 20)
If X is negative, N must be an odd integer.

1 Commento

Perfect. the nthroot function does exactly what I'm asking. It works not only for this problem but 3 other similar problems of y functions of x with fractional exponents. Thank you

Accedi per commentare.

Più risposte (1)

x=-1:0.01:8; y=@(x) (x).^(4/3); yinv=@(x) -((x).^(4/3)); x_1=-1; x_2=8;
[xmin, ymin]=fminbnd(y,x_1,x_2);
[xmax, ymax]=fminbnd(yinv,x_1,x_2);
fprintf('The local maximum is %.2f at x = %.2f\n', -ymax, xmax)
The local maximum is 16.00 at x = 8.00
fprintf('The local minimum is %.2f+%.2fi at x = %.2f\n', real(ymin), imag(ymin), xmin)
The local minimum is -0.50+0.87i at x = -1.00
fprintf() ignores the imaginary component of numbers.

5 Commenti

This is the closest you can get to forcing MATLAB to only give real solutions to a math function using fminbnd
x=-1:0.01:8; y=@(x) (x).^(4/3); yinv=@(x) -((x).^(4/3)); x_1=-1; x_2=8;
opts = optimset('FunValCheck', 'on');
[xmin, ymin] = fminbnd(y, x_1, x_2, opts);
Error using matlab.internal.optimfun.utils.checkfun/nestedThrowError (line 48)
Objective function '@(x)(x).^(4/3)' returned a complex value when evaluated at -0.188471. FMINBND cannot continue.

Error in matlab.internal.optimfun.utils.checkfun (line 17)
nestedThrowError("Complex");

Error in fminbnd>@(x,varargin)matlab.internal.optimfun.utils.checkfun(x,funfcn,"fminbnd",varargin{:}) (line 211)
funfcn = @(x, varargin) matlab.internal.optimfun.utils.checkfun(x, funfcn, "fminbnd", varargin{:});

Error in fminbnd (line 325)
fu = funfcn(x,varargin{:});
[xmax, ymax] = fminbnd(yinv, x_1, x_2, opts);
fprintf('The local maximum is %.2f at x = %.2f\n', -ymax, xmax)
fprintf('The local minimum is %.2f+%.2fi at x = %.2f\n', real(ymin), imag(ymin), xmin)
I sort of lie a little:
You can set an option OutputFcn that checks the appropriate condition and records the current coordinates if the condition passes, and signals "stop" if the condition does not pass; then once the function finishes, retrieve the recorded coordinates.
Hi Walter I might be asking the wrong question. Can MATLAB give this answer?
(-1)^(4/3)=1
This is probably not the principal root of (-1)^(4/3) but that's what TI-84 also gives.
The realpow and/or nthroot functions may also be of interest.
x1 = (-1)^(1/3)
x1 = 0.5000 + 0.8660i
x2 = nthroot(-1, 3)
x2 = -1
x = roots([1, 0, 0, 1]) % all three roots
x =
-1.0000 + 0.0000i 0.5000 + 0.8660i 0.5000 - 0.8660i

Accedi per commentare.

Categorie

Prodotti

Release

R2021a

Community Treasure Hunt

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

Start Hunting!

Translated by