2010-02-07 3 views
3

regardant http://download.eclipse.org/jetty/stable-7/xref/com/acme/ChatServlet.html, je ne semble pas comprendre pourquoi il doit y avoir un bloc de synchronisation dans une méthode synchronisée, comme suit:aide de synchronisation en Java

private synchronized void chat(HttpServletRequest request,HttpServletResponse response,String username,String message) 
throws IOException 
{ 
    Map<String,Member> room=_rooms.get(request.getPathInfo()); 
    if (room!=null) 
    { 
     // Post chat to all members 
     for (Member m:room.values()) 
     { 
      synchronized (m) 
      { 
       m._queue.add(username); // from 
       m._queue.add(message); // chat 

       // wakeup member if polling 
       if (m._continuation!=null) 
       { 
        m._continuation.resume(); 
        m._continuation=null; 
       } 
      } 
     } 
    } 

Pourquoi m doivent être synchronisées (encore une fois ?) si toute la méthode est déjà thread-safe?

Nous vous remercions de votre compréhension.

Répondre

4

La méthode synchronisée "chat (...)" se synchronise sur son objet instance alors que le synchronisé (m) se synchronise sur l'objet "m" - donc ils se synchronisent sur deux objets différents. Fondamentalement, il s'assure qu'un autre objet servlet ne joue pas avec la même instance de membre en même temps.

+0

Merci, je comprends, mais juste par curiosité ... pourquoi l'objet _rooms n'est-il pas également synchronisé? –

+1

Probablement parce que _rooms est seulement modifié par d'autres méthodes synchronisées dans la même classe, aussi longtemps que vous y accédez dans une méthode synchronisée, vous pouvez être sûr que personne ne l'ajoute ou en supprime des éléments. Idéalement, il serait défini comme «privé» car, à l'heure actuelle, il est paquet-privé, ce qui signifie que toutes les autres classes du paquet (ou sous-classes) pourraient y accéder. –

+0

Merci pour votre commentaire, mais alors je dois revenir à ma question initiale. Pourquoi synchroniser 'm' est-il nécessaire? Il est seulement utilisé dans des méthodes déjà synchronisées (un peu comme _rooms). Ou synchroniser 'm' juste une précaution? –

1

Lorsque la méthode entière est synchronisée, le verrou est obtenu sur l'objet this. Mais le bloc synchronisé n'obtient le verrou que sur le membre en cours d'itération.

0

La synchronisation s'effectue sur différents verrous.

Le mot-clé synchronized à la définition de la méthode signifie que tout autre code qui se synchronise sur this ne peut pas s'exécuter en parallèle à la méthode.

La portée synchronized(m) signifie qu'un autre code qui se synchronise sur m ne peut pas s'exécuter parallèlement à la boucle.