Mathematica: Fortschritt und Restrechenzeit anzeigen

Führt man in Mathematica zeitaufwändige Berechnungen durch, so wünscht man sich oft eine Fortschrittsanzeige um den Status der Berechnung zu erfahren. Eine einfache Fortschrittsanzeige kann man mit der Funktion ProgressIndicator realisieren.

Als erstes definiert man eine Variable, die den aktuellen Fortschritt beschreibt. Wird beispielsweise ein Feld durchlaufen, so gibt diese Variable die Position, an der gerade eine Berechnung durchgeführt wird an. Ich nenne sie hier iter.

Anschließend benutzt man die Funktion ProgressIndicator und übergibt als Argument den Iterator (iter), wobei man angeben muss, dass er dynamisch ist.

ProgressIndicator[Dynamic[iter], {1, maxIter}]

Um jetzt den Fortschritt einer Berechnung anzuzeigen muss man in der Berechnung dem Iterator immer die aktuelle Laufvariable zuweisen.

Am Beispiel von Selectionsort könnte es so aussehen:

maxIter = 1000; (* Maximale Anzahl von Zahlenwerten *)

iter = 0; (* aktueller Fortschritt.  iter <= maxIter *)

(* Fortschrittsbalken einbauen. iter gleich maxIter –> 100% *)
ProgressIndicator[Dynamic[iter], {1, maxIter}]  


(* Liste mit Zufallswerten *)
numb = Table[Random[Integer, {1, 10000}], {x, 1, maxIter}];

(* Selectionsort *)
For[i = 1, i < maxIter, i++,
 minpos = i;
 For[j = i + 1, j <= maxIter, j++,
  If[numb[[j]] < numb[[minpos]], 
   minpos = j, 
   ]
  ];
 temp = numb[[i]];
 numb[[i]] = numb[[minpos]];
 numb[[minpos]] = temp;
 iter = i; (* iterator aktualisieren*)
 ]

Fortschrittsbalken

Optimal wäre natürlich auch eine Restrechenzeitangabe. Die einfachste Möglichkeit ist eine lineare Zeitinterpolation, die je nach dem wie man den Iterator setzt für eine Abschätzung der Restzeit gut genug sein soll.

Fügt man den diesen Codeblock anstatt ProgressIndicator in dem oberen Beispiel…

Dynamic[
 {{"Status:", 
    ProgressIndicator[iter, {0, maxIter}], (iter/maxIter)*100.0, "%"},
   {"Restzeit (min):", 
    AccountingForm[((maxIter - 
          iter)/((iter + 0.0001)/(AbsoluteTime[] - startTime)))/
      60, {Infinity, 1}], "", ""}} // MatrixForm
 ]
startTime = AbsoluteTime[];

… so sieht die Aussage folgendermaßen aus.
Fortschrittsbalken

Viel Spaß beim Warten und Tee trinken ;)

Schreibe einen Kommentar