2010-05-06 3 views
2
public static synchronized void main(String[] args) throws InterruptedException { 
    Thread t = new Thread(); 
    t.start(); 
    System.out.print("X"); 
    t.wait(10000); 
    System.out.print("Y"); 
    } 
  • Quel est le problème avec cette méthode?
  • Comment puis-je éviter de tels problèmes à partir de maintenant?

Répondre

2

Il existe quelques problèmes avec ce code. Je pense que vous essayez d'écrire quelque chose comme ceci:

public static synchronized void main(String[] args) throws InterruptedException { 
    System.out.print("X"); 
    Thread.sleep(10000); 
    System.out.print("Y"); 
} 

La méthode Thread.sleep() suspend le thread courant pendant l'intervalle spécifié. Object.wait() est quelque chose d'autre entièrement et il est peu probable que c'est ce que vous voulez.

Vous pouvez voir comment j'ai éliminé le fil t. Si vous voulez vraiment créer un fil séparé et que les impressions soient produites sur ce fil, vous devez donner quelque chose au fil. La meilleure façon de le faire est de méthode remplacement run() du fil et avoir le code de fil il y a:

public static synchronized void main(String[] args) { 
    Thread t = new Thread() { 
    public void run() { 
     System.out.print("X"); 
     try { Thread.sleep(10000); } catch (InterruptedException e) { } 
     System.out.print("Y"); 
    } 
    }; 

    t.start(); 
} 

Comme l'écrit votre code d'origine était en fait la création d'un fil sans corps de fil, donc lorsque vous appelez t.start() le vide le fil commencerait simplement en arrière-plan et mourrait immédiatement.

Notez que j'ai dû ajouter une clause try/catch pour InterruptedException maintenant que l'appel de veille a migré vers l'intérieur du thread. run() n'est pas autorisé à lancer des exceptions alors maintenant, malheureusement, nous devons attraper et ignorer l'exception.

Une autre façon d'écrire ceci serait de faire une partie du travail dans le fil t et le reste du travail dans votre fil principal. Voici un exemple de la façon dont vous pourriez fendit le travail en deux fils:

public static synchronized void main(String[] args) throws InterruptedException { 
    Thread t = new Thread() { 
    public void run() { 
     System.out.print("X"); 
     try { Thread.sleep(10000); } catch (InterruptedException e) { } 
    } 
    }; 

    t.start(); 
    t.join(); 

    System.out.print("Y"); 
} 

Lorsque cela appelle t.join() il attendra le fil à la fin d'exécution, qui prendra 10 secondes, car il dort. Une fois le thread terminé, la méthode join() va revenir et permettre au thread principal de continuer. Le résultat final apparaîtra le même pour l'utilisateur: le programme imprimera X, fera une pause pendant 10 secondes, puis affichera Y.

1

Eh bien, les suggestions de John feront l'affaire. Mais vous pourriez toujours sentir flou concernant l'exception s'est produite. Pour cela, je voudrais que vous lisiez la documentation de la méthode Object.wait(), et de IllegalMonitorStateException. Après avoir lu ceux-ci, une question pourrait vous venir à l'esprit: que diable est le moniteur d'Object? Donc, ici, il est de wikibooks,

Chaque objet a un «moniteur d'objet». Fondamentalement, il s'agit d'un «sémaphore» , indiquant si un code de section critique est exécuté par un thread ou non. Avant qu'une section critique puisse être exécutée, le thread doit obtenir un 'Moniteur d'objet'. Seul un fil à la fois peut posséder ce moniteur d'objet .

Questions connexes