Langsame Journale?
Laufzeitvergleich zwischen NX Open .NET Journalen und compilierten Programmen.
Inhaltsverzeichnis
Ob ich bei der Umsetzung eines NX Zusatzprogramms auf ein Journal1 oder eine compilierte Lösung setze, hängt von vielen verschiedenen Faktoren ab. Falls eine bestimmte Programmiersprache für die Realisierung vorgesehen ist, besteht unter Umständen keine Wahl. C/C++ und Java müssen immer compiliert werden. Pythonprogramme liegen immer als Skript vor.
Die .NET Sprachen C# und VB.NET können in NX sowohl compiliert als auch uncompiliert zum Einsatz kommen. Hier kann das Antwortverhalten und die Ablaufgeschwindigkeit ein wichtiger Faktor für die Auswahl der einen oder anderen Variante sein. Es ist naheliegend, dass compilierte .NET Programme einen Geschwindigkeitsvorteil besitzen. Wie groß ist dieser Unterschied jedoch tatsächlich? Welchen Auswirkung hat er in der Praxis?
Hintergrund
Uncompilierte .NET NX Open Journale werden nicht zur Laufzeit interpretiert. Der Quellcode wird bei jedem Aufruf des Journals mit dem im .NET Framework standardmäßig vorhandenen Compiler übersetzt, geladen und dann regulär ausgeführt. Während des Programmlaufes kann man das entsprechende Assembly unter dem Namen journal.dll im von NX verwendeten temporären Verzeichnis finden. Nach Abschluss des Programmlaufes wird diese dll jedesmal durch NX gelöscht.
Für die Ausführungsgeschwindigkeit des eigentlichen Programminhaltes bedeutet das interessanterweise, dass compilierte Programme keinen Vorteil gegenüber uncompiliert vorliegenden Journalen haben können. In der Gesamtbilanz kommt jedoch bei den Journalen der Overhead zur internen Compilierung hinzu. Dieser Overhead vergrößert die Antwortzeit der Applikation nach dem Start.
Ein weiterer Aspekt muss bei der Betrachtung zusätzlich berücksichtigt werden. Bei compilierten Programmen kann die Entladeoption für das Assembly festgelegt werden (Immediately, At Termination, Explicitly). Bei Journalen wird diese Option im Quelltext ignoriert. Die Assemblys von Journalen werden nach dem Programmende immer entladen (Immediately). Compilierte Programme können also bei Bedarf davon profitieren, dass NX die Assemblys für eine erneute Ausführung im Speicher vorhält.
Testaufbau
Da, wie gezeigt, für die Fragestellung nur der Overhead zum Compilieren und das Entladeverhalten relevant sind, kann ein sehr einfaches Testprogramm verwendet werden. Es enthält lediglich die Ausgabe eines Markers in die NX-Logdatei.
using NXOpen;
using System;
public class SmallUi
{
public static int Main(string[] args)
{
int retValue = 0;
Session.GetSession().LogFile.WriteLine("%%%SUI");
return retValue;
}
public static int GetUnloadOption(string arg)
{
return System.Convert.ToInt32(Session.LibraryUnloadOption.Immediately);
}
}
Um den Einfluss der Quelltextgröße festzustellen wurde ein weiteres Programm erstellt, das vom ausgeführten Inhalt her dem ersten entspricht. Zusätzlich wurde der Quellcode eines mittelgroßen realen Projektes so hinzugefügt, dass er zwar mitcompiliert, aber nicht ausgeführt wird. Entstanden ist dabei eine Quellcodedatei mit rund 2700 Zeilen.
Von beiden Programmen wurde je eine Variante mit der Entladeoption Immediately (direkt nach Programmende) und At Termination (beim Beenden von NX) erstellt, compiliert und mit der Authoring-Lizenz signiert. Die Quellcodes des kurzen und des langen Programmes können zudem direkt als Journale ausgeführt werden. Damit ergeben sich insgesamt 6 zu testende Varianten:
- SUI: Kurzes Programm, compiliert, Entladen direkt nach Programmende
- SUAT: Kurzes Programm, compiliert, Entladen beim Beenden von NX
- SUIJ: Kurzes Programm, Ausführung als Journal
- BUI: Langes Programm, compiliert, Entladen direkt nach Programmende
- BUAT: Langes Programm, compiliert, Entladen beim Beenden von NX
- BUIJ: Langes Programm, Ausführung als Journal
Um die Laufzeit der verschiedenen Programme zu ermitteln, dient zusätzlich ein kleines Programm das lediglich einen Zeitstempel in die NX Log-Datei schreibt. Weiterhin wurde eine MenuScript-Datei (.men) erstellt, die für jede der genannten 6 Varianten einen Action Button mit einer aufeinderfolgenden Folge von Aktionen in NX erzeugt.
...
BUTTON SMALLUI
LABEL Small UI
ACTIONS ${mypath}time\application\time.dll
ACTIONS ${mypath}time\application\time.dll
ACTIONS ${mypath}time\application\time.dll
ACTIONS ${mypath}time\application\time.dll
ACTIONS ${mypath}time\application\small_ui.dll
ACTIONS ${mypath}time\application\time.dll
ACTIONS ${mypath}time\application\time.dll
ACTIONS ${mypath}time\application\time.dll
ACTIONS ${mypath}time\application\time.dll
ACTIONS ${mypath}time\application\time.dll
ACTIONS ${mypath}time\application\small_ui.dll
ACTIONS ${mypath}time\application\time.dll
...
Auf diese Weise werden die einzelnen Programme auf einen Kopfdruck unmittelbar hintereinander durch NX ausgeführt. Zur Auswertung können die Zeitstempel und die Marker der eigentlichen Programme aus der Logdatei ausgelesen werden. Aus dem Abstand zweier einen Marker umschließender Zeitstempel abzüglich des Abstands zweier direkt aufeinander folgender Zeitstempel kann die tatsächliche Laufzeit der zu testenden Variante ermittelt werden. In ersten Versuchen zeigte sich, dass immer wieder Ausreißer bei der Laufzeit des Zeitstempelprogrammes auftraten. Deshalb wird das Zeitstempel-Programm mehrfach hintereinander aufgerufen und zur Berechnung der Laufzeiten der eigentlichen Programme der Median verwendet.
Für jede der 6 Programmvarianten wurden 9 Läufe mit einem jeweils neu gestartetem NX durchgeführt. Die Laufzeiten für den ersten und den zweiten Programmaufruf ergeben sich wiederum aus dem Median dieser 9 Läufe. Die ermittelten Werte sind ein Maß für das Antwortverhalten der verschiedenen Varianten.
Die Tests wurden unter NX1953 auf einer älteren Workstation mit Xeon CPU durchgeführt. Die Ergebnisse sind nur qualitativ auf andere Systeme übertragbar.
Ergebnisse
Die Abbildung zeigt die Ergebnisse für die kurze Programmvarianten. Die vollständige Laufzeit beträgt für die compilierten Varianten knapp 0,6 Sekunden beim ersten Start (SUI (1), SUAT (1)). Beim zweiten Start ist die Laufzeit auf rund 0,2 Sekunden reduziert, wenn die dll vorher nicht entladen wurde (SUAT (2)). Wurde die dll entladen (SUI (2)), entspricht die Laufzeit der des Erststarts. Die Journal-Varianten (SUIJ (1), SUIJ (2)) haben eine deutlich längere Laufzeit von rund 1,2 Sekunden. Der zweite Lauf ist geringfügig schneller als der erste.
Die Abbildung zeigt die Ergebnisse für die lange Programmvariante. Auch hier beträgt die Laufzeit für die compilierten Varianten knapp 0,6 Sekunden beim ersten Start (BUI (1), BUAT (1)) und 0,2 Sekunden beim zweiten Start, wenn die dll vorher nicht entladen wurde (BUAT (2)). Das uncompilierte Journal (BUIJ) hat mit 1,4 Sekunden eine etwas längere Laufzeit als die kurze Version.
Fazit
Insgesamt zeigen die Messungen kein Überraschungen. Uncompilierte Journale benötigen für den Start und das Beenden deutlich mehr Zeit als ihre compilierten Gegenstücke. Idealerweise beträgt die Antwortzeit auf eine Benutzerinteraktion weniger als eine Sekunde (siehe z.B. 2 oder 3). Die compilierten Programme liegen alle deutlich unter dieser Marke. Journale zeigen ein schlechteres Antwortverhalten. Die Werte sind allerdings nicht so hoch, dass der Arbeitsfluss unterbrochen wird.
Der Einfluss der Quellcodegröße auf die Startdauer der Programme ist compiliert wie uncompiliert gering.
Hinsichtlich der Ablaufgeschwindigkeit des eigentlichen Programminhaltes gibt es keinen Unterschied zwischen compilierten und uncompilierten Applikationen.
Wenn die Responsivität eine sehr große Rolle spielt, dann sind compilierte NX Open .NET Applikationen vorzuziehen. In allen anderen Fällen können durchaus auch Journale verwendet werden.
-
Der Begriff Journal wird im erweiterten Sinn häufig auch für NX Open-Programme allgemein verwendet. Hier sind aber ausschließlich in VB.NET oder C# realisierte Programme gemeint, die direkt als Quellcode ausgeführt werden. ↩︎
-
Michael Herczeg, Software-Ergonomie, Addison-Wessley 1994, S.203 ↩︎
-
https://developer.gnome.org/hig-book/unstable/feedback-response-times.html.en ↩︎