Recherche des zéros d'une fonction

Problème : On cherche \(x_0\) tel que \(f(x_0) \simeq 0\).

La fonction fzero permet de résoudre ce problème.

Il faut fournir d'une part la fonction \(f\) elle-même, et d'autre part une estimation de \(x_0\). L'efficacité de l'algorithme est comme toujours dépendante de la valeur estimée choisie.

La fonction \(f\) peut-être définie dans une fichier ou par l'intermédiaire d'une fonction anonyme.

Exemple

Par exemple on cherche le zéro de :

\[f(x) = x - \cos \left( x \right)\]

Une approche graphique permet souvent de trouver une estimation de \(x_0\). La figure suivante montre ainsi que les fonctions \(x \rightarrow x\) et \(x \rightarrow \cos\left( x\right)\) se coupent en un point sur \([-\pi, \pi]\), dans le voisinage de 1. C'est la raison pour laquelle \(x_0\) sera choisie égale à cette valeur.

Estimation de x0 par approche graphique
Estimation de x0 par approche graphique

On peut résoudre ce problème et trouver la racine en définissant une fonction anonyme :

>> f = @(x) (x-cos(x)) ;
>> fzero(f,1)
 
ans =
    0.7391

On remarquera que la variable f envoyée à la fonction fzero fait référence à une fonction, puisqu'elle contient la définition d'une fonction anonyme. Toutes les fonctions de calcul numérique de MATLAB nécessitant l'écriture d'une fonction par l'utilisateur fonctionnent selon ce principe.

L'autre option est de définir la fonction dans un fichier f.m :

function y = f(x)
    y = x - cos(x);
end

L'utilisation de fzero se fait ensuite selon une des deux syntaxes suivantes :

>> racine = fzero('f',1) ;

ou

>> racine = fzero(@f,1) ;

Remarque

Si l'on cherche plusieurs racines, il sera nécessaire de modifier la valeur d'initialisation pour espérer trouver de nouvelles racines. Encore une fois, on insistera donc sur l'importance du choix de la valeur d'initialisation de la recherche.

Remarque

fzero impose que \(f\) ne dépende que d'une variable (\(x\) dans notre exemple).

Si \(f\) est une fonction de plusieurs variables, fzero permet de déterminer le zéro de cette fonction que le long d'une seule de ses dimensions, autrement dit, les autres variables doivent être considérées comme des paramètres.

cas des fonctions paramétriques

On veut chercher le zéro de la fonction

\[f(x) = x - \cos \left(mx \right) \]

\(m\) est un paramètre susceptible de varier.

La meilleure solution est d'utiliser une fonction anonyme :

>> m=1;
>> f = @(x) x - cos(m*x) ;
>> racine1 = fzero(f,1)
 
  racine1 =
    0.7391
 
>> m=2 ;
>> f = @(x) x - cos(m*x) ;
>> racine2 = fzero(f,1)
 
  racine2 =
    0.5149

Attention

Selon cette écriture, la fonction \(f\) est bien définie comme étant une fonction à une seule variable \(x\), et comportant un paramètre m. Malheureusement, si l'on veut modifier la valeur de m, il faut aussi redéfinir la variable f ...

Complémentfonction anonyme de fonction anonyme

Pour éviter de devoir redéfinir la fonction anonyme à chaque fois que l'on veut modifier la valeur du paramètre, il faut définir deux fonctions anonymes !

  • La première correspond à la fonction mathématique qui nous intéresse, c'est-à-dire, la fonction comportant deux arguments : la variable x et le paramètre m.

  • La seconde est la fonction anonyme argument de fzero. C'est une fonction qui ne dépend que de x, puisque l'on recherche le zéro en x, pour une valeur de m donnée.

>> fm = @(x,m) x - cos(m*x) ;
>> racine1 = fzero( @(x) fm(x,1), 1)
 
  racine1 =
    0.7391
 
>> racine2 = fzero( @(x) fm(x,2), 1)
 
  racine2 =
    0.5149
 

Remarque

Une autre solution consiste à définir \(f\) dans un fichier f.m est de créer la variable m en utilisant la directive global (voir section Portée des variables[1]).

La fonction \(f\) s'écrira donc :

function y = f(x)
    global m
    y = x-cos(m*x);
end

et on cherchera son zéro en écrivant un script principal :

>> global m
>> m = 1;
>> racine = fzero(@f,0)