notes·de·pit

Parfois j'apprends à pêcher à des gens qui n'aiment pas le poisson

Débuguer son code sans utiliser d'IDE…

carpenter-bee.jpg

Écrire un code sans erreur est une gageure que bla bla bla. J’ai écrit du code, je constate qu’il ne fonctionne pas, comment faire pour le débuguer ?

La méthode, peut-être la plus simple, est de lancer un IDE (Netbeans ou autre) et de jouer avec son outil de débugage. Je place des points d’arrêt dans mon code et je trace le programme… cette méthode nécessite le recours à un IDE et demandera un peu de temps de prise en main. On peut lire le how to Netbeans à ce sujet.

Il existe cependant d’autres manières de faire qui peuvent être plus appropriées dans le cas de projets simples…

Avertissement Je ne parle pas de JUnit dans la suite car je parle bien de débuguer son code et non de le tester. Ce sont, pour moi, deux tâches différentes (et toutes les deux indispensables… quoique les bisounours peuvent sans doute se passer de débugage)



Comment débuguer son code ?

Débuguer un code, c’est trouver et quand le code devient mauvais et pourquoi ? Il existe plusieurs types d’erreurs; les erreurs de compilation et de syntaxe, les erreurs logiques et les erreurs à l’exécution (runtime). En Java, les erreurs de compilation et de syntaxe sont rapidement détectées grâce au compilateur.

Pour détecter les autres erreurs;

Si l’on ne sait pas par où commencer, il suffit de commencer par la première instruction de la méthode main.

Pour débuguer son code, il existe différentes techniques

La méthode de l’homme pauvre (poor man)

La première méthode, celle que l’on préconise pour les débutants, consiste à placer des instructions sout1 dans son code afin de voir le contenu de certaines variables ou simplement de savoir si le programme « passe bien » par certaines instructions.

System.out.println("DEBUG (...)");

On évitera des commentaires de style « coucou », « passe par ici » et l’on préfèrera toujours commencer par le mot « DEBUG ». Ceci afin de pouvoir facilement retrouver ce type de commentaire dans son code.

Cette méthode, bien que qualifiée d’archaïque, fait le boulot et peut convenir lorsqu’un débutant veut débuguer un programme (moyennement) simple. L’inconvénient de la méthode est qu’il faudra retirer ces commentaires à un moment donné.

Si l’on veut améliorer un peu la méthode, on peut placer à l’endroit qui va bien une variable booléenne précisant si l’on veut les commentaires de débugage ou pas (on peut même envisager que cette valeur soit un argument du programme). Le code aura alors l’allure suivante

private static boolean debugEnabled = true;
// (...)
if (debugEnabled) System.out.println("DEBUG - <mon commentaire>");

Utilisation des assertions

Cette technique peut venir en complément de la précédente. Le mécanisme consiste à placer à certains endroits du code un check du style; « je suppose que mon programme est dans cet état, sinon arrête toi ». Ce test consiste le plus souvent à tester l’état d’une ou plusieurs variables.

You can use assertions to detect errors that may otherwise go unnoticed. Assertions contain Boolean expressions that define the correct state of your program at specific points in the program source code.

Extrait de http://java.sun.com/developer/technicalArticles/JavaLP/assertions/

Cette méthode est liée au design by contract (design-by-contract model of programming voir Qusay) qui, pour moi, peut être résumé par

Par exemple: Un traitement consiste en le calcul d’une racine carrée: précondition, le nombre doit être positif.

Une assertion s’exprime à l’aide d’une expression booléenne. Lorsque celle-ci est fausse, le programme s’arrête et génère une exception. Une assertion peut être affublée d’un message spécifique.

Board b = null; 
// on essaie de créer ce plateau de jeu 
b = new Board();
 
assert b != null;
// ou
assert b != null : "Can't create game board";

En Java, ce mécanisme est disponible depuis Java 1.42. Par défaut les assertions ne sont pas utilisées au runtime. Ajouter ces instructions dans le code ne fait donc que « grossir » le code mais ne le font pas « ralentir ». Pour que ces assertions soient testées, il faut le dire à la machine virtuelle par le biais de l’option enableassertion.

java -ea my.package.MyClass
java -enableassertions my.package.MyClass

Utilisation d’un débugueur, jdb

Java est fourni avec un débugueur (malheureusement) en ligne de commande. Pour pouvoir l’utiliser, il faut demander au compilateur de générer un bytecode qui pourra être utilisé par jdb. Cela se fait grâce à l’option -g (l’option -O est alors à proscrire car un code optimisé ne pourra pas être débugué). Ensuite, lancer le débugueur

java -g MyClass.java
jdb MyClass

Les commandes comprise par jdb sont (entre autres)

Une séance de débugage avec le code (erroné) suivant peut avoir l’allure décrite brièvement ci-dessous

public class TestJdb { 
     public static void main ( String[] args ) { 
          int i; 
          i = 5;
          i = foo(i); 
     }
 
     public static int foo(int i){ 
         // Attention, c'est sans doute mieux --i;
         return i--;
     }
}

En quelques images;

jdb-2.png

jdb-3.png

jdb-4.png

L’utilisation d’un débugueur demandera un certain temps d’adaptation avant de pouvoir correctement tracer son programme.

Enjoy !

Note d’orthographe

Certains utilisent le mot débogage puisqu’ils recherchent des bogues dans le programme… ce sont les plus proches de l’académie française.

D’autres utilise le mot débugage car ils sont à la recherche de bugs dans leur programme… ce sont les plus enclins à moins françiser les mots.

… l’important c’est de pouvoir se comprendre ;-)

Sources / Liens

À (re)lire aussi


  1. comprendre System.out.println par exemple 

  2. À l’heure où j’écris on en est au JDK 7