Hjælpesiden til FindRoot siger:

“som standard, FindRoot bruger Newtons metode (Newton-Raphson) til at løse et ikke-lineært system”

(eller en ikke-lineær ligning antager jeg). Ikke desto mindre er der noget skjult for mig i kommandoen FindRoot. Overvej funktionen

f[x]:=Exp[1 - x] - 1, 

hvis Newton-iterationsfunktion er

Nf[x_]:=E^(-1 + x) (-1 + E^(1 - x)) + x 

Itererer med denne funktion ved hjælp af NestList du får rækkefølgen af værdier produceret efter Newtons metode. Newton-metoden til store værdier af det første gæt præsenterer langsom konvergens for dette problem. At tage $ x_0 = 10 $ får vi:

NestList[Nf, 10., 8] (* {10., -8092.08, -8091.08, -8090.08, -8089.08, -8088.08, -8087.08, -8086.08, -8085.08} *) 

hvor vi kan se langsom konvergens. Et plot af funktionen Nf[x] hjælper med at forstå metodens opførsel. Men at tage

Module[{s = 0, e = 0}, {FindRoot[f[x], {x, 10.}, StepMonitor :> s++, EvaluationMonitor :> e++], "Steps" -> s, "Evaluations" -> e}] 

producerer

{{x -> 1.}, "Steps" -> 7, "Evaluations" -> 11} 

behøver kun 7 trin for at få løsningen $ x = 1 $. Hvorfor FindRoot giver dette resultat ?. Det er klart, at FindRoot ikke bruger Newtons standardmetode, er det ikke? Kan nogen hjælpe mig? Tak.

Kommentarer

Svar

Som standard FindRoot bruger "LineSearch" metoden til trinkontrol som beskrevet i vejledningen tutorial/UnconstrainedOptimizationLineSearchMethods . Standardindstillingerne er

FindRoot[Exp[1 - x] - 1, {x, 10.}, Method -> {"Newton", "StepControl" -> {"LineSearch", "CurvatureFactor" -> Automatic, "DecreaseFactor" -> 1/10000, "MaxRelativeStepSize" -> 10, Method -> Automatic}}] 

For at få Newtons metode mere eller mindre nøjagtigt skal du ikke bruge nogen trinkontrol. FindRoot begrænser stadig den maksimale trinstørrelse (det første trin i nedenstående tilfælde er afkortet til x == -100.):

Module[{s = 0, e = 0}, {FindRoot[Exp[1 - x] - 1, {x, 10.}, Method -> {"Newton", "StepControl" -> None}, StepMonitor :> s++, EvaluationMonitor :> e++], "Steps" -> s, "Evaluations" -> e}] 

FindRoot :: cvmit: Kunne ikke konvergere til den ønskede nøjagtighed eller præcision inden for 100 iterationer. >>

(* {{x -> -1.07713}, "Steps" -> 100, "Evaluations" -> 101} *) 

Du kan bruge indstillingerne

StepMonitor :> Print[{x}], EvaluationMonitor :> Print[x] 

til at overvåge trinene og evalueringerne. Eller du kan brug FindRootPlot i "Optimization`UnconstrainedProblems`" -pakken. (Se nøje efter de gule prikker, der angiver en evaluering, der ikke er et trin.)

Needs["Optimization`UnconstrainedProblems`"] FindRootPlot[Exp[1 - x] - 1, {x, 10.}, PlotRange -> All] 

Mathematica-grafik

FindRootPlot[Exp[1 - x] - 1, {x, 10.}, Method -> {"Newton", "StepControl" -> None}, PlotRange -> All] 

Mathematica-grafik

Kommentarer

  • Sæt det på en anden måde: FindRoot[] bruger en dæmpet version af Newton-Raphson, for uden dæmpning vil dårlige valg af startværdier oftere resultere i divergens. Dæmpningen gør gentagelserne mindre tilbøjelige til at blive vilde.

Skriv et svar

Din e-mailadresse vil ikke blive publiceret. Krævede felter er markeret med *