# Conseils de codage en C/Lisibilité des sources

Maintenabilité
* Pour la lisibilité
* Pour la détection des erreurs
* Pour des modifications plus faciles
Fiabilité
* Pour la robustesse
* Pour les performances
* Pour la sécurité
Qualité
* Pour une utilisation plus facile
* Pour la qualité numérique
Maintenabilité
* Pour la lisibilité
* Pour la détection des erreurs
* Pour des modifications plus faciles
Fiabilité
* Pour la robustesse
* Pour les performances
* Pour la sécurité
Qualité
* Pour une utilisation plus facile
* Pour la qualité numérique
Livre
[ Modifier le sommaire ]
Les conseils suivants rendent les logiciels plus maintenables.
Leur respect a pour but de :
* faciliter la lecture des codes sources écrits en C
* diminuer l'effort nécessaire pour diagnostiquer les déficiences ou causes de défaillance, ou pour identifier les parties à modifier.

## Cartouche d'entête (c_lis_1)

Chaque fichier source (.c, .h) et chaque fonction C doivent être précédés d’un cartouche qui pourra contenir :
* Le nom de l'unité ou de la fonction.
* Son rôle et ses points de programmation critiques.
* Pour une fonction, la description des arguments et des codes retours.
* La date, l’auteur et le rôle de chaque modification.
* Sa licence et droits d'utilisation
* La mention de documents de conception ou de référence

### Justification

Le cartouche de l’unité permet de faciliter sa compréhension d'un point de vue général. Les cartouches de fonctions permettent de comprendre leur rôle et conditions d'appel sans se plonger dans le code source . Ces entêtes sont indispensables à la gestion de la configuration et à la maintenance.

### Outils

* La plupart des environnements de développement bâtissent un squelette de cartouche d'entête lors de la création d'un nouveau fichier
* Pour les projets importants, développés en équipe, les versions des fichiers sources pourront être gérées par un logiciel spécialisé comme CVS, subversion...
* L'utilisation d'un outil de gestion de la documentation comme Doxygen permet, à l'aide d'une syntaxe particulière dans les commentaires, de générer à partir des sources la documentation de programmation du projet.

## Indentation des instructions (c_lis_2)

Les instructions imbriquées sont indentées à l’aide de tabulations ou d'espaces de façon homogène dans tous les fichiers sources du projet.

### Justification

La maintenance et la relecture des sources sont facilités par une présentation homogène.

### Outils

* L'outil UNIX indent permet d'améliorer la présentation des fichiers sources écrits en C. De nombreuses options permettent de paramètrer le style de ses sorties. Elles peuvent être passées sur la ligne de commande ou mieux dans un fichier de configuration spécifique.

## Indentation des commentaires (c_lis_3)

Les commentaires suivent l’indentation des instructions de code.

### Justification

Augmente la lisibilité.

## Une instruction par ligne (c_lis_4)

Ne pas écrire plus d'une instruction par ligne.

### Justification

Augmente la lisibilité.

## Décomposer les instructions longues (c_lis_5)

Coder des lignes simples.

### Justification

Il est quelquefois tentant de coder des lignes longues :
* Dans le domaine numérique, le programmeur écrit des formules compliquée juxtaposant de nombreuses fonctions et opérateurs.
* Le langage C permet de mélanger tests, appel de fonctions, opérations.
Le code parait, à première vue, plus compact, plus efficace. Il faut cependant décomposer les lignes longues en plusieurs, en utilisant des variables intermédiaires. Les compilateurs récents se chargeront d'optimiser efficacement le code pour vous. Le résultat sera plus facile à comprendre par d'autres. Les problèmes de priorité pourraient être atténués.

## Constantes symboliques et macros en majuscule (c_lis_6)

Les noms des constantes symboliques et des macros instructions doivent être écrits en majuscule.

### Justification

Dans un fichier source, permet des distinguer rapidement les constantes des variables.

### Exemple
## Pas de lignes trop longues (c_lis_7)

Les instructions ne doivent pas dépasser la colonne 80. Les instructions longues doivent être placées sur plusieurs lignes.

### Justification

Les lignes courtes seront plus faciles à comprendre par une personnes chargée de maintenir le logiciel.

### Exemples

Mauvais :
Meilleur :

## Nommage des identificateurs (c_lis_8)

Vous devez donner des noms significatifs aux identificateurs.
* Évitez les noms trop courts sans signification fonctionnelle : v, vv, vvv...
* Ne différenciez pas deux identificateurs uniquement en changeant la casse de certains caractères : Fichier, fichier.
* Ne différenciez pas deux identificateurs uniquement par un nombre trop restreint de lettres.
* N'utilisez pas de caractère souligné en tête ou en fin d'identificateur.
* Utiliser une règle de nommage cohérente dans le projet : mot séparés par des soulignés (fichier_parametres_calcul) ou mots collés commençant par des majuscules sauf première lettre (fichierParametresCalcul).

### Justification

Facilite la lisibilité et la maintenabilité.

## Cohérence des identificateurs (c_lis_9)

Dès lors qu’un identificateur de variable est défini pour une entité significative, il faut utiliser ce même identificateur quelle que soit l’unité de code considérée.

### Justification

Facilite l'analyse du programme.

## Arguments du programme principal (c_lis_10)

Les arguments du programme principal sont standards : int main(int argc, char *argv)

### Justification

Améliore la lisibilité du code. argv[0] représente le nom de lancement du programme et peut être utilisé pour les messages d'erreur. La récupération des arguments du programme pourra se faire avec les fonctions getopt, getsubopt.

## Limiter l'utilisation des opérateurs ++ et -- (c_lis_11)

Les opérateurs ++ et -- ne sont autorisés que pour les indices de boucles et les pointeurs, à condition qu’aucun autre opérateur n’apparaisse et que seule l’utilisation post-fixée soit utilisée.

### Justification

Facilite l’analyse et la maintenance par des programmeurs habitués à d’autres langages.

### Exemple

* Correct : for (i=0; i<n; i++) {//....
* Moins bon : t[i++]=f(i++);

## Limiter l'utilisation de l'opérateur de test ternaire (c_lis_12)

L’utilisation de l’expression conditionnelle ? : est interdite en dehors des macros.

### Justification

Facilite l’analyse et la maintenance par des programmeurs habitués à d’autres langages.

## Ne pas économiser les accolades (c_lis_13)

Utilisez des accolades autour d'une ou des instructions d'un bloc. Ce bloc peut faire partie d’une structure de contrôle comme if - else - for - do - while.

### Justification

Rend le code plus lisible et évite les erreurs lors de l'ajout d'une instruction dans un bloc qui n'en contient qu'une seule.

### Exemple

Mauvais :
Meilleur :
Exemple d'erreur provoquée par la violation de ce conseil :
L'instruction table2[i] = 2; donne faussement l'impression de faire partie de la boucle for, ce qui est renforcé par l'indentation et l'accolade fermante du if.
Si table2 était dimensionné à n, les indices acceptables iraient de 0 à n-1 inclus. Lors de l'exécution de l'instruction table2[i] = 2;, i vaudrait la valeur n, ce qui provoquerait l'écriture d'une valeur hors de l'espace mémoire réservé pour le tableau table2.
Il s'en suivra :
* Le débordement hors de l'espace utilisateur qui provoquera une violation mémoire : Sanction rapide par arrêt du programme exception SIGSEGV.
* L'écrasement du contenu d'un autre pointeur situé juste après l'espace table2 qui lorsqu'il sera utilisé plus tard (100 lignes plus bas ?) provoquera une autre catastrophe : Cette erreur peut être difficile à détecter sans l'utilisation d'un outil qualité d'analyse dynamique.
* Ces erreurs peuvent arriver aléatoirement selon le système, le compilateur utilisé ou le chargement du programme en mémoire.

## Bien aligner les accolades (c_lis_14)

Une accolade fermante se trouve toujours à la verticale de l’accolade ouvrante correspondante.

### Justification

Permet de mieux repérer les blocs d'instructions conditionnelles, les corps de boucles surtout en cas de structures imbriquées.

### Exemple
## Éviter d'utiliser les opérateurs d'affectation spécifique au C (c_lis_15)

L’utilisation de l’assignation composée (+=, -=, *=, %=, /=) et de l’affectation multiple (v1 = v2 = v3;) est déconseillée.

### Justification

Facilite l’analyse et la maintenance par des programmeurs habitués à d’autres langages.

## Ne pas déclarer plusieurs variables dans la même instruction (c_lis_16)

Il faut déclarer chaque variable séparément et non les unes à la suite des autres, séparées par des virgules.

### Justification

La déclaration de plusieurs variables dans une même instruction peut provoquer des erreurs de type pour les variables.
Une déclaration séparée permet aussi de décrire dans un commentaire en bout de ligne le rôle de chaque variable.

### Exemple
## Seuils pour les métriques déterminant la facilité d'analyse (c_lis_17)

Les métriques suivantes influent sur la facilité d'analyse d'un programme (ISO/IEC 9126) :
* VG : nombre cyclomatique : nombre de chemins linéairement indépendants dans un graphe connexe g, V(g) = A - N + 1 avec A : nombre de graphe entre les nœuds du graphe et N : nombre de nœuds du graphe.
* STMT : Nombre d'instructions exécutables entre les accolades de début et de fin de la fonction.
* FCOM : Fréquence des commentaires : F_COM = (BCOM+BCOB) / STMT, avec BCOM = Nombre de blocs de commentaires dans la fonction, BCOB : nombre de blocs de commentaires avant la fonction.
* AVGS : Taille moyenne des instructions, calculée à partir du nombre d'opérateur et d'opérande distincts.
Seuils pour les métriques :
* VG : de 1 à 20
* STMT : de 1 à 100
* FCOM : de 0,2 à 1,2
* AVGS : de 2 à 10

### Justification

* VG trop élevée montre qu'une fonction est trop complexe et mériterait d'être décomposée en plusieurs ou réanalysée.
* STMT trop élevée indique que la fonction est trop longue. Il faudrait la diviser ou peut-être appeler des fonctions.
* FCOM : Habituellement les programmes ne sont pas assez commenté : FCOM faible. Cependant un programme avec trop de commentaires peut aussi montrer des problèmes (trop de ruses d'un expert qui aurait dû écrire plus simplement ???).
* AVGS : Les instructions trop longues sont difficiles à comprendre et peuvent provoquer des problèmes de priorité des opérateurs, de conversion de type involontaires.