2012-10-27 20 views
5

Ich möchte diese Bibliothek verwenden, die ich gefunden habe, es ist ein reiner Java-Port (kein Wrapper) von Zeromq. Ich versuche es zu testen und während es claims einige gute Zahlen, der Test, den ich ausführe, gibt eher schlechte Ergebnisse und es wird sogar vor Ort durchgeführt (Client und auf der gleichen Maschine dienen). Ich bin mir sicher, dass ich etwas falsch mache. Es dauert ca. 5 Sekunden, um diese 10.000 Nachrichtenschleife auszuführen.Warum ist dieser JeroMQ (ZeroMQ Port) Benchmark so langsam?

Alles, was ich getan habe, ist das Hello World Beispiel nehmen und Pause und Sysouts entfernt. Hier ist der Code:

Der Server:

package guide; 

import org.jeromq.ZMQ; 

public class hwserver{ 
    public static void main(String[] args) throws Exception{ 

     // Prepare our context and socket 
     ZMQ.Context context = ZMQ.context(1); 
     ZMQ.Socket socket = context.socket(ZMQ.REP); 

     System.out.println("Binding hello world server"); 
     socket.bind ("tcp://*:5555");   

     while (true) {     
      byte[] reply = socket.recv(0); 
      String requestString = "Hello" ; 
      byte[] request = requestString.getBytes();    
      socket.send(request, 0);    
     }    
    } 
} 

Der Kunde:

package guide; 

import org.jeromq.ZMQ; 

public class hwclient{ 
    public static void main(String[] args){ 
     ZMQ.Context context = ZMQ.context(1); 
     ZMQ.Socket socket = context.socket(ZMQ.REQ); 
     socket.connect ("tcp://localhost:5555"); 

     System.out.println("Connecting to hello world server"); 

     long start = System.currentTimeMillis(); 
     for(int request_nbr = 0; request_nbr != 10_000; request_nbr++) { 
      String requestString = "Hello" ; 
      byte[] request = requestString.getBytes();   
      socket.send(request, 0); 
      byte[] reply = socket.recv(0);   
     } 
     long end = System.currentTimeMillis(); 
     System.out.println(end-start); 
     socket.close(); 
     context.term(); 
    } 
} 

Ist es möglich, diesen Code zu beheben und ein paar anständige Zahlen zu bekommen?

+0

Andere haben geantwortet, wie man schnellere Zahlen bekommt - indem man etwas anderes macht. Ich möchte nur darauf hinweisen, dass Ihre absoluten Zahlen nicht unbedingt schlecht sind: Im Durchschnitt 0,5 ms pro Rundmeldung. Und als Teil des Roundtrip wird die Nachricht in eine Hochsprache geparst und eine verarbeitete Version davon zurückgesendet. Vergleichen Sie das mit den Zahlen, die Sie mit einem einfachen ICMP-Ping erhalten, und Sie bekommen ein Gefühl für den Overhead von TCP, JeroMQ und Ihrem Code. –

Antwort

13

Sie tun Round-Trip-Anfrage-Antwort, und das wird genauso langsam mit dem C++ libzmq. Sie erhalten nur eine schnelle Leistung bei JeroQM, ZeroMQ oder einem beliebigen I/O beim Streaming.

Round-tripping ist langsam, da I/O und TCP arbeiten. Auf libzmq können wir etwa 20K Nachrichten/Sekunde mit Round-Triping und 8M/Sek. Mit Streaming machen. Beim Streaming gibt es zusätzliche Optimierungen wie die Stapelverarbeitung, die Sie mit der Round-Trip-Anfrage-Antwort nicht ausführen können.

Senden Sie für einen Durchsatzleistungstest 10M Nachrichten von Knoten 1 an Knoten 2 und senden Sie dann einen einzelnen ACK zurück, wenn Sie sie erhalten. Zeit, dass auf ZeroMQ und JeroMQ, sollten Sie etwa 3x Unterschied in der Geschwindigkeit sehen.

3

Bitte beachten Sie den Durchsatztest zwischen synchroner Hin- und Rückfahrt und asynchronem Round-Trip bei

https://github.com/zeromq/jeromq/blob/master/src/test/java/guide/tripping.java

Die asynchronen war x40 schneller als die synchrone Hin- und Rückfahrt.

Wenn Sie die volle Geschwindigkeit von jeromq messen möchten, führen Sie perf.LocalThr und perf.RemoteThr für Ihre Umgebung aus.