Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

A problem with FindRoot

509 views
Skip to first unread message

Vassilis Dimitrakas

unread,
Nov 29, 2007, 6:29:29 AM11/29/07
to
Hi All,

I'd like some help with respect to a problem I have with the FindRoot,
NSolve and FindInstance functions.
My version of Mathematica is 5.2

I define the function f as follows:

f[x_]:={
y/.FindRoot[y^3+1==x,{y,x}][[1]]
}[[1]]

f[x] returns the root of the equation y^3 + 1 == x, i.e. the value
(x-1)^(1/3). f[x] has obviously a
unique root at x=1.

If I now try to find f[x]'s root with FindRoot, for example like

FindRoot[f[x]==0,{x,3}]

Mathematica (v 5.2) returns error messages and no solution. The same
happens if I use instead NSolve
or FindInstance. Can you guys explain why this happens and suggest a
remedy?

Thanks,

Vassilis


Szabolcs Horvát

unread,
Nov 30, 2007, 5:49:09 AM11/30/07
to

Try evaluating f[x]. You get the same errors. The function f should
only be evaluated with a numerical argument. So use

f[x_?NumericQ] := Module[{y}, y /. FindRoot[y^3 + 1 == x, {y, x}]]

instead. Note that all those lists and indices are not necessary, but
'y' should be made a local variable to avoid unpleasant surprised when
it is given a value.

--
Szabolcs

DrMajorBob

unread,
Nov 30, 2007, 6:02:24 AM11/30/07
to
NumericQ fixes the problem (for the most part):

Clear[f]
f[x_?NumericQ] := y /. First@FindRoot[y^3 + 1 == x, {y, x}]
FindRoot[f[x] == 0, {x, 3}]

FindRoot::lstol: The line search decreased the step size to within \
tolerance specified by AccuracyGoal and PrecisionGoal but was unable \
to find a sufficient decrease in the merit function. You may need \
more than MachinePrecision digits of working precision to meet these \
tolerances. >>

{x -> 1.}

The precision warning occurs for a very good reason, as a plot shows:

Plot[f@x, {x, 0, 5}]

Gradient methods obviously won't work well at such a point.

In addition, you're starting the inner (first) FindRoot at y = x (the
current value). To converge in the final problem x must approach 1, but y
must approach 0, so on EVERY iteration of the inner problem you're
starting far from the solution, learning nothing from previous iterations.
FindRoot manages anyway, but only barely.

So this is no way to do things unless it's really necessary.

In this case a nice option is

Clear[f]
f[x_] = Last@
Simplify[Reduce[{y^3 + 1 == x, y \[Element] Reals}, {y}], x >= 0];
Plot[f@x, {x, 0, 5}]
Reduce[f[x] == 0, x]

x == 1

Bobby

On Thu, 29 Nov 2007 05:24:03 -0600, Vassilis Dimitrakas
<vdimi...@googlemail.com> wrote:

> Hi All,
>
> I'd like some help with respect to a problem I have with the FindRoot,
> NSolve and FindInstance functions.
> My version of Mathematica is 5.2
>
> I define the function f as follows:
>
> f[x_]:={
> y/.FindRoot[y^3+1==x,{y,x}][[1]]
> }[[1]]
>
> f[x] returns the root of the equation y^3 + 1 == x, i.e. the value
> (x-1)^(1/3). f[x] has obviously a
> unique root at x=1.
>
> If I now try to find f[x]'s root with FindRoot, for example like
>
> FindRoot[f[x]==0,{x,3}]
>
> Mathematica (v 5.2) returns error messages and no solution. The same
> happens if I use instead NSolve
> or FindInstance. Can you guys explain why this happens and suggest a
> remedy?
>

> Thanks,
>
> Vassilis
>
>
>

--

DrMaj...@bigfoot.com

Murray Eisenberg

unread,
Nov 30, 2007, 6:03:25 AM11/30/07
to
You didn't say what error message Mathematica 5.2 gives.

In Mathematica 6.0.1 (and probably in 5.2 as well), the first thing is
to ensure that you use numeric values only, so define:

f[x_?NumericQ] := Last@First@FindRoot[y^3 + 1 == x, {y, x}]

(Except for the ?NumericQ qualification on x, this accomplishes the same
thing you had.) This eliminates the error message:

FindRoot::srect: "Value x in search specification {y,x} is not a
number or array of numbers. "

Next, just

FindRoot[f[x], {x, 3}]

generates a different error message, namely:

FindRoot::lstol: The line search decreased the step size to within \
tolerance specified by AccuracyGoal and PrecisionGoal but was unable \
to find a sufficient decrease in the merit function. You may need \
more than MachinePrecision digits of working precision to meet these \
tolerances.

So do what the error message suggests: increase the allowed number of
iterations or accuracy goal. For example:

FindRoot[f[x], {x, 3}, AccuracyGoal -> 10^-16]
{x->1.05086}

Does this help?

Vassilis Dimitrakas wrote:
> Hi All,
>
> I'd like some help with respect to a problem I have with the FindRoot,
> NSolve and FindInstance functions.
> My version of Mathematica is 5.2
>
> I define the function f as follows:
>
> f[x_]:={
> y/.FindRoot[y^3+1==x,{y,x}][[1]]
> }[[1]]
>
> f[x] returns the root of the equation y^3 + 1 == x, i.e. the value
> (x-1)^(1/3). f[x] has obviously a
> unique root at x=1.
>
> If I now try to find f[x]'s root with FindRoot, for example like
>
> FindRoot[f[x]==0,{x,3}]
>
> Mathematica (v 5.2) returns error messages and no solution. The same
> happens if I use instead NSolve
> or FindInstance. Can you guys explain why this happens and suggest a
> remedy?
>
> Thanks,
>
> Vassilis
>
>

--
Murray Eisenberg mur...@math.umass.edu
Mathematics & Statistics Dept.
Lederle Graduate Research Tower phone 413 549-1020 (H)
University of Massachusetts 413 545-2859 (W)
710 North Pleasant Street fax 413 545-1801
Amherst, MA 01003-9305

Jean-Marc Gulliet

unread,
Nov 30, 2007, 6:08:30 AM11/30/07
to
Vassilis Dimitrakas wrote:

I bet that the error messages you get are a similar to "FindRoot::srect:

"Value x in search specification {y,x} is not a number or array of numbers."

Add a condition to your definition of f so it is called only for numeric
arguments.

In[1]:= Clear[f]
f[x_?NumberQ] := {y /. FindRoot[y^3 + 1 == x, {y, x}][[1]]}[[1]]
FindRoot[f[x] == 0, {x, 3}, AccuracyGoal -> 5]

Out[3]= {x -> 1.}

Regards,
--
Jean-Marc

Szabolcs Horvát

unread,
Dec 1, 2007, 6:04:45 AM12/1/07
to
Jean-Marc Gulliet wrote:
> I bet that the error messages you get are a similar to "FindRoot::srect:
> "Value x in search specification {y,x} is not a number or array of numbers."
>
> Add a condition to your definition of f so it is called only for numeric
> arguments.
>
> In[1]:= Clear[f]
> f[x_?NumberQ] := {y /. FindRoot[y^3 + 1 == x, {y, x}][[1]]}[[1]]
> FindRoot[f[x] == 0, {x, 3}, AccuracyGoal -> 5]
>
> Out[3]= {x -> 1.}

I'd just like to add a small comment: In these situations it is more
correct to use NumericQ instead of NumberQ, otherwise expressions like
f[Sqrt[2]] will not evaluate. Sqrt[2] is not an "atomic" number in
Mathematica, but a compound expression. However, it does represent a
number in the mathematical sense, and N[Sqrt[2]] evaluates to a floating
point value. So NumberQ[Sqrt[2]] === False and NumericQ[Sqrt[2]] ===
True. Of course this does not make a difference if the function f is
only used inside FindRoot[].

--
Szabolcs

0 new messages