[9] Fonctions inline (intégrées)
(Une partie de C++ FAQ Lite fr, Copyright © 1991-2002, Marshall Cline cline@parashift.com )

Traduit de l'anglais par Jérôme Lecomte

Les FAQs de la section [9]


[9.1] Quel est le contrat avec les fonctions inline?

Une fonction inline(en ligne) est une fonction dont le code est inséré directement dans le flux de code de la fonction appelante. Comme les macro #define, les fonctions inline améliorent la vitesse d'exécution en éliminant l'en-tête d'appel et (sutout!) en permettant au compilateur d'optimiser à traversl'appel ("intégration procédurale").

[ Haut | Bas | Section précédente | Section suivante ]


[9.2] Comment les fonctions inline aident à améliorer le compromis entre sûreté et vitesse?

En C pur, vous pouvez réaliser des "structs (structures) encapsulées" en mettant un void *dans un struct, où le void *pointe sur les vraies données qui sont inconnues aux utilisateurs du struct. Ainsi ces même utilisateurs du struct ne peuvent pas interpréter les données pointées par void *, mais les fonctions d'accès peuvent elles convertir du void *vers le type de données caché. Ce qui donne une forme de l'encapsulation.

Malheureusement ceci impose de renoncer à la sûreté de type, et impose également un appel de fonction pour accéder même aux zones insignifiantes du struct (si vous permettiez l'accès direct au champs du struct, chacun pourrait accèder directement à tout le struct puisqu'il connaîtrait nécessairement les données pointées par void *, et il deviendrait difficile de changer la structure de données sous-jacentes).

Le temps passé dans l'en-tête d'appel de fonction est court, mais il s'ajoute à chaque appel. Les classes C++ permettent à ces appels de fonction d'être insérés inline. Ceci vous laisse la sûreté de l'encapsulation avec en plus la vitesse des accès directs. En outre, les types des paramêtres de ces fonctions inline sont contrôlées par le compilateur, ce qui est une amélioration par rapport aux macros #define du C.

[ Haut | Bas | Section précédente | Section suivante ]


[9.3] Pourquoi devrais-je utiliser les fonctions inline? et non simplement les vieilles macros #define?

Parce que les macros #definesont mauvaises.

Contrairement aux macros #define, les fonctions inline évitent les erreurs infâmes liées aux macros puisque les fonctions inline évaluent toujours chaque argument une fois exactement. En d'autres termes, appeler une fonction inline est sémantiquement équivalent à appeler une fonction régulière, mais plus rapidement:

    // Une macro qui retourne la valeur abolue de i
    #define unsafe(i)  \
            ( (i) >= 0 ? (i) : -(i) )

    // Une fonction inline qui retourne la valeur absolue de i
    inline
    int safe(int i)
    {
      return i >= 0 ? i : -i;
    }

    int f();

    void codeUtilisateur(int x)
    {
      int rep;

      rep = unsafe(x++);   // Erreur! x est incremente deux fois
      rep = unsafe(f());   // Danger! f() is appele deux fois

      rep = safe(x++);     // Correct! x est incremente une fois
      rep = safe(f());     // Correct! f() est appele une fois
    }

Egalement au crédit des fonctions inline par rapport aux macros #define, les types d'argument sont contrôlés, et les conversions nécessaires sont exécutées correctement.

Les macros #define sont mauvaises pour votre santé; ne les utilisez pas à moins d'y être contraint.

[ Haut | Bas | Section précédente | Section suivante ]


[9.4] Comment dites-vous au compilateur de mettre une fonction non membre inline?

Quand vous déclarez une fonction inline, elle a exactement l'aspect d'une fonction normale:

    void f(int i, char c);

Mais quand vous définissez une fonction inline, vous ajoutez au début de la définition de la fonction le mot-clé inline, et vous mettez la définition dans le fichier d'en-tête:

    inline
    void f(int i, char c)
    {
      / / ...
    }

Note: Il est impératif que la définition de la fonction (la partie entre {...}) soit placé dans un fichier d'en-tête, à moins que la fonction soit utilisée seulement dans ce seul fichier .cpp. En particulier, si vous mettiez inline la définition de la fonction dans un fichier cpp et vous l'appeliez d'un autre fichier, vous obtiendriez "une erreur externe" (fonction non définie) au moment de l'édition de liens.

[ Haut | Bas | Section précédente | Section suivante ]


[9.5] Comment dites vous au compilateur de considérer une fonction membre inline?

Quand vous déclarez inlineune fonction membre, elle a exactment l'aspect d'une fonction membre normale :

    class Fred {
    public:
      void f(int i, char c);
    };

Mais quand vous définissez une fonction membre inline, vous ajoutez au début de la définition de la fonction membre le mot-clé inline, et vous mettez la définition dans un fichier d'en-tête:

    inline
    void Fred::f(int i, char c)
    {
      / / ...
    }

Il est habituellement impératif que la définition de la fonction (la partie entre {... }) soit placé dans un fichier d'en-tête. Si vous mettiez inline la définition d'une fonction dans un fichier d'implémentation cpp, et si cette fonction était appellée d'un autre fichier cpp, vous obtiendriez "une erreur externe" (fonction non définie) au moment de l'édition de liens.

[ Haut | Bas | Section précédente | Section suivante ]


[9.6] Y a-t-il un autre moyen de spécifier une fonction membre inline?

Oui: définissez la fonction de membre dans le corps de classe elle-même:

    class Fred {
    public:
      void f(int i, char c)
        {
          / / ...
        }
    };

Bien que ce soit plus facile pour la personne qui écrit la classe, c'est aussi plus dur pour le lecteur puisqu'on mélange "ce que fait" la classe avec "comment elle le fait". En raison de ce mélange, on préfère normalement définir des fonctions de membre en dehors du corps de classe avec le mot-clé inline. Comprenez que dans un monde orienté objet et réutilisation, il y a beaucoup de gens qui utilise la classe, mais une seule personne qui la créé (vous même); c'est pourquoi vous devriez faire les choses en faveurs du plus grand nombre plutôt que pour le plus petit.

[ Haut | Bas | Section précédente | Section suivante ]


[9.7] Est-ce que les fonctions inline garantissent une meilleure performance?

Non.

Gardez à l'esprit qu'une overdose de fonctions inline peut ammener le code à gonfler exagérement, ce qui peut avoir un impact négatif sur l'exécution dans des environnements paginé.

[ Haut | Bas | Section précédente | Section suivante ]


E-mail Marshall Cline Ecrire à l'auteur, au traducteur, ou en savoir plus sur la traduction.
[ C++ FAQ Lite fr | Table des matières | Index | A propos de l'auteur | © | Téléchargez votre propre copie ]
Dernière révision le 12 Nov 2002