5

Ich habe versucht herauszufinden, warum es so lange dauert, unser Programm im Debugging-Modus zu debuggen. Nach der Verwendung von xperf, um zu sehen, wie die Stacks aussahen, war es offensichtlich, dass wir einen großen Teil unserer Zeit in den Iterator und die STL-Container investierten. Ich googeln dies für eine Weile und fand die OptionenWarum verursachen Iteratoren in VS2010 ein sehr langsames Debuggen, obwohl _HAS_ITERATOR_DEBUGGING, _SECURE_SCL, _SECURE_SCL_THROWS auf 0 gesetzt sind 0

_HAS_ITERATOR_DEBUGGING=0 
_SECURE_SCL=0 
_SECURE_SCL_THROWS=0 

Und ich brachte alle diejenigen in Code mit einer #define

#define _HAS_ITERATOR_DEBUGGING 0 
#define _SECURE_SCL 0 
#define _SECURE_SCL_THROWS 0 

Aber das schien nicht zu arbeiten, so ist, dann habe ich versucht, es zu benutzen die Präprozessor-Definitionen innerhalb des Visual Studio-Projekts, aber das schien immer noch nicht zu helfen.

Ich habe fast jede mögliche Permutation ausprobiert, einschließlich der Einstellung in den Headern und nach all den Includes, aber egal was ich mache, ich sehe keine Leistungssteigerung während des Debuggens. Um ein Beispiel zu geben, benötigt diese Reihe von Operationen im Freigabemodus ungefähr 140 Sekunden. Im Debug-Modus dauert es etwas über 2400 Sekunden. Etwa 17- bis 18-fache Verlängerung der Verarbeitungszeit.

Einige zusätzliche Informationen, der Prozess, der diese C++ - DLLs hostet, ist ein C# .net 4-Prozess, und ich habe das Debuggen nicht verwalteten Codes aktiviert. Im Grunde alle Prozess lädt es die DLLs für uns. Die ganze wirkliche Arbeit wird im C++ Code erledigt.

Ich habe die vollständige Compiler-Befehlszeile darunter eingefügt.

/I"..\CommonInclude" /Zi /nologo /W4 /WX /Od /Oy- /D "_CRT_SECURE_NO_WARNINGS" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_USRDLL" /D "ENGINE_EXPORTS" /D "_HAS_ITERATOR_DEBUGGING=0" /D "_SECURE_SCL=0" /D "_SECURE_SCL_THROWS=0" /D "_VC80_UPGRADE=0x0710" /D "_WINDLL" /D "_MBCS" /Gm- /EHa /MDd /GS /fp:precise /Zc:wchar_t- /Zc:forScope /GR /Yu"StdAfx.h" /Fp".\Debug/Foo.pch" /Fa".\Debug/" /Fo".\Debug/" /Fd".\Debug/" /Gd /analyze- /errorReport:queue /EHa -Zm350 /MP3 

Irgendwelche Ideen, warum das so langsam wäre wie es ist?

+0

Es ist ein Debug-Build; Es ist zum Debuggen gedacht, nicht zur Leistung. Es soll sicherstellen, dass Ihr Code funktioniert. –

+0

Iterator-Debugging ist nicht * das * langsam. Es ist wahrscheinlicher, dass der Code nicht optimiert wird. Die Problemumgehung ist einfach. Verwenden Sie nur kleinere Datasets, um Ihren Code zu überprüfen. Die Wahrscheinlichkeit, dass Sie einen Fehler mit hundert Mal mehr Daten ausgleichen, ist nicht so toll. –

Antwort

1

Eine Sache, die einen großen Unterschied macht, ist, dass standardmäßig Funktionen im Debug-Modus nicht inline sind. Das fügt eine Menge Zeit hinzu, um Code zu verwenden, der viele kleine Accessor-Funktionen verwendet.

Ich habe Programme, bei denen der Unterschied zwischen Debug- und Release-Modus ein Faktor 100+ ist, ohne von Iteratoren abhängig zu sein.

1

Ein paar Dinge zu versuchen:

  • einen Profiler verwenden, zum Beispiel der freien AMD CodeAnalyst, wie es Ihnen Callstacks geben wird und ist als Xperf im Allgemeinen zu verwenden, viel einfacher. Auch wenn Sie mit Debug-Code zu tun haben, finden Sie möglicherweise noch einige Hotspots
  • Erstellen Sie einen Release-Build mit deaktivierten Optimierungen (Sie könnten eine separate Konfiguration dafür erstellen). Dies wird das Debuggen des Iterators ausschalten (falls dies der Grund für Ihre Verlangsamung ist), kann jedoch viel nützlichere Debugging-Informationen liefern als ein roher Release-Build. Überprüfen Sie, ob die Option Rahmenzeiger wegzulassen ist
  • aktiviert
7

Basierend auf Ihrer Beschreibung, springt diese sofort aus:

Ich habe versucht, auf die Spur, warum es so lange dauert unser Programm zu debuggen wenn im Debugging-Modus. Nach der Verwendung von Xperf, um zu sehen, was die Stacks aussahen, war es offensichtlich, dass wir eine große Menge unserer Zeit im Iterator und die STL-Container ausgaben.

Wenn Sie die Knoten-basierten Container verwenden (zB map, set, unordered_map, unordered_set, multimap, multiset, list, etc.), und aus dem Debugger ausführen, können Probleme auftreten, die aus diesen Behältern stammen Zuordnen einer Tonne von Objekten mit kleinen Größen. Wenn Sie eine Anwendung vom Debugger in Windows ausführen, wechselt das Betriebssystem den Prozess-Heap in den Debug-Heap. Wenn Sie viele knotenbasierte Container unter Last haben, wird das Freigeben von ihnen viel Zeit mit dem Debug-Heap beanspruchen.

Eine einfache Lösung ist, indem es das folgende Kapitel Umwelt der Debug-Optionen, um den Debug-Heap zu deaktivieren: _NO_DEBUG_HEAP=1

Das deaktiviert den Debug-Heap.