Ich mache ein Kopier-Einfüge-Programm für die Übung. Was ich bemerkte ist, dass die Aktualisierung der UI im while
Betrieb der I/O, drossle ich die Übertragungsgeschwindigkeit bis zu 40%. Was 4 Sekunden nahm jetzt 8.Java I/O Loop-Drosselung aufgrund von UI-Updates
Zum Beispiel kopieren nimmt:
int b;
long total = 0;
byte[] buf = new byte[4096];
while ((b = in.read(buf)) != -1) {
out.write(buf, 0, b);
ui.setSoFar(total);
total += b;
}
Die ui.setSoFar()
nur ruft die setText()
Methode auf einem JLabel
in einem JFrame
Die out
und in
Vars sind ein FileInputStream
und FileOutputStream
.
Mit einem Kingston SHF37A/120G gedrosselt auf SATA II-Geschwindigkeiten dauert das Kopieren einer 313MB-Datei etwa 8 Sekunden, was etwa 40 MB/s entspricht.
Wenn ich den Code ändern, wie folgt aussehen:
int b;
byte[] buf = new byte[4096];
while ((b = in.read(buf)) != -1) {
out.write(buf, 0, b);
}
, die eine einfache Schleife ist, nichts in-zwischen den Lese- und Schreib, eine 313MB-Datei Kopieren dauert etwa 3 Sekunden, die 100 MB/s ist .
Das ist fast ein Unterschied von 60% bei der Ausgabe!
Wie zu lösen, damit ich noch eine UI aktualisieren und die 100% Übertragungsgeschwindigkeit beibehalten kann, nicht verlieren die 60%?
Nun, mit 40MB/s und Aktualisieren der Benutzeroberfläche alle 4096 Bytes, aktualisieren Sie die Benutzeroberfläche etwa 10'000 mal pro Sekunde - niemand ist so schnell die Benutzeroberfläche lesen gegangen. Versuchen Sie, die Benutzeroberfläche weniger häufig zu aktualisieren (möglicherweise alle 400'000 Bytes) –
Nun, die Puffergröße ist gestiegen, die Frage ist, gibt es irgendwelche Nebenwirkungen? Es ist jetzt wesentlich schneller tho. Vielen Dank. – Gala
Dies ist ein guter Kandidat für die Verwendung von [SwingWorker] (https://docs.oracle.com/javase/8/docs/api/javax/swing/SwingWorker.html). – VGR