Hinweis
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, sich anzumelden oder das Verzeichnis zu wechseln.
Für den Zugriff auf diese Seite ist eine Autorisierung erforderlich. Sie können versuchen, das Verzeichnis zu wechseln.
Das Konkurrenzvisualisierungswerkzeug hilft Entwicklern, das Verhalten einer Multithread-Anwendung zu visualisieren. Dieses Tool enthält einen Katalog allgemeiner Muster für Multithread-Anwendungen, die sich schlecht verhalten. Der Katalog enthält typische und erkennbare visuelle Muster, die über das Tool verfügbar gemacht werden, zusammen mit einer Erläuterung des Verhaltens, das durch jedes Muster dargestellt wird, das wahrscheinliche Ergebnis dieses Verhaltens und der häufigste Ansatz, um es zu beheben.
Sperren von Inhalten und serialisierter Ausführung
Manchmal wird eine parallelisierte Anwendung auch weiterhin fortlaufend ausgeführt, obwohl sie mehrere Threads enthält und der Computer über eine ausreichende Anzahl von logischen Kernen verfügt. Das erste Symptom ist eine schlechte Multithreadleistung, vielleicht sogar etwas langsamer als eine serielle Implementierung. In der Threadsansicht werden nicht mehrere Threads parallel ausgeführt. Stattdessen sehen Sie, dass immer nur ein Thread ausgeführt wird. Wenn Sie an diesem Punkt auf ein Synchronisierungssegment in einem Thread klicken, wird ein Aufrufstapel für den blockierten Thread (blockierender Aufrufstapel) und der Thread angezeigt, der die Blockierungsbedingung entfernt hat (Entsperrung des Aufrufstapels). Wenn der Entsperrungsaufrufstapel in dem Prozess auftritt, den Sie analysieren, wird außerdem ein Thread-Ready Connector angezeigt. Von diesem Punkt aus können Sie von den Blockierungs- und Entsperrungsaufrufstapeln zu Ihrem Code navigieren, um die Ursache der Serialisierung noch mehr zu untersuchen.
Wie in der folgenden Abbildung dargestellt, kann der Concurrency Visualizer dieses Symptom auch in der CPU-Auslastungsansicht aufdecken, wobei die Anwendung trotz des Vorhandenseins mehrerer Threads nur einen logischen Kern nutzt.
Weitere Informationen finden Sie im MSDN-Magazin-Artikel „Thread Performance – Resource Contention Concurrency Profiling in Visual Studio“ im Abschnitt „Mit dem Problem beginnen“.
Ungleiche Workloadverteilung
Wenn eine unregelmäßige Verteilung der Arbeit über mehrere parallele Threads in einer Anwendung erfolgt, wird ein typisches Treppenschrittmuster angezeigt, da jeder Thread seine Arbeit abschließt, wie in der vorherigen Abbildung dargestellt. Der Concurrency-Visualizer zeigt meistens sehr eng beieinanderliegende Startzeiten für jeden gleichzeitigen Thread an. Diese Threads enden jedoch in der Regel unregelmäßig, anstatt gleichzeitig zu enden. Dieses Muster gibt eine unregelmäßige Verteilung der Arbeit zwischen einer Gruppe paralleler Threads an, was zu einer verringerten Leistung führen kann. Der beste Ansatz für ein solches Problem besteht darin, den Algorithmus neu zu bewerten, durch den die Arbeit in den parallelen Threads aufgeteilt wurde.
Wie in der folgenden Abbildung dargestellt, kann der Concurrency Visualizer dieses Symptom in der CPU-Auslastungsansicht auch als eine allmähliche Verringerung der CPU-Auslastung aufzeigen.
Überzeichnung
Bei Überschreibung ist die Anzahl der aktiven Threads in einem Prozess größer als die Anzahl der verfügbaren logischen Kerne im System. Die vorherige Abbildung zeigt die Ergebnisse der Übersubscription mit erheblichen Preemption-Effekten in allen aktiven Threads. Darüber hinaus zeigt die Legende, dass ein großer Prozentsatz der Zeit für die Unterbrechung (84 Prozent in diesem Beispiel) aufgewendet wird. Dies kann darauf hindeuten, dass der Prozess das System auffordern, mehr gleichzeitige Threads auszuführen als die Anzahl der logischen Kerne. Dies kann jedoch auch darauf hindeuten, dass andere Prozesse im System Ressourcen verwenden, die für diesen Prozess als verfügbar angenommen wurden.
Sie sollten Folgendes berücksichtigen, wenn Sie dieses Problem auswerten:
Das Gesamtsystem kann überlastet sein. Berücksichtigen Sie, dass andere Prozesse auf dem System möglicherweise Ihre Threads unterbrechen. Wenn Sie in der Threadansicht über ein Preemption-Segment anhalten, identifiziert eine QuickInfo den Thread und den Prozess, der den Thread unterbrochen hat. Dieser Prozess ist nicht unbedingt derjenige Prozess, der während der gesamten Zeit ausgeführt wurde, in der Ihr Prozess verdrängt wurde, sondern gibt einen Hinweis darauf, was den Verdrängungsdruck gegen Ihren Prozess erzeugt hat.
Bewerten Sie, wie Ihr Prozess die entsprechende Anzahl von Threads für die Ausführung in dieser Phase der Arbeit bestimmt. Wenn Ihr Prozess die Anzahl der aktiven parallelen Threads direkt berechnet, sollten Sie diesen Algorithmus ändern, um die Anzahl der verfügbaren logischen Kerne im System besser zu berücksichtigen. Wenn Sie die Parallelitätslaufzeit, die Task Parallel Library oder PLINQ verwenden, führen diese Bibliotheken die Arbeit zur Berechnung der Anzahl der Threads aus.
Ineffiziente E/A
Übernutzung oder Missbrauch von E/A ist eine häufige Ursache für Ineffizienzen in Anwendungen. Betrachten Sie die vorherige Abbildung. Das Profil der sichtbaren Zeitachse zeigt, dass 44 Prozent der sichtbaren Thread-Laufzeit von E/A verbraucht werden. Die Zeitachse zeigt große E/A-Mengen an, was darauf hinweist, dass die profilierte Anwendung häufig durch E/A blockiert wird. Um Details zu den Arten von E/A und darüber, wo Ihr Programm blockiert ist, anzuzeigen, zoomen Sie in problematische Bereiche, untersuchen Sie das sichtbare Zeitachsenprofil und klicken Sie dann auf einen bestimmten E/A-Block, um aktuelle Anrufstapel anzuzeigen.
Lock konvoys
Lock-Konvois treten auf, wenn die Anwendung Sperren in der Reihenfolge „Wer zuerst kommt, mahlt zuerst“ erwirbt und wenn die Ankunftsrate an der Sperre höher ist als die Erwerbsrate. Die Kombination dieser beiden Bedingungen führt dazu, dass Anforderungen auf die Sperre sich zu stauen beginnen. Eine Möglichkeit zur Bekämpfung dieses Problems ist die Verwendung von "unfairen" Sperren, also Sperren, die dem ersten Thread, der sie im entsperrten Zustand vorfindet, Zugriff gewähren. Die vorherige Abbildung zeigt dieses Konvoyverhalten. Um das Problem zu lösen, versuchen Sie, die Konkurrenz um Synchronisierungsobjekte zu reduzieren und unfaire Sperren zu verwenden.