2009-04-21 13 views
5

Sto vivendo una cosa strana negli ultimi due giorni. Ho scoperto che la mia versione di Release esegue effettivamente più lenta rispetto alla versione di debug.. La versione di rilascio di .NET funziona più lentamente di Debug

1. Il problema

ho finalmente messo a nudo tutta roba dal mio punto di ingresso (principale) nel mio Windows Form exe, lasciando solo questo:

[STAThread] 
static void Main(params string[] args) 
{ 
    Stopwatch sw = Stopwatch.StartNew(); 
    System.Xml.Serialization.XmlSerializer xmlS = 
     new System.Xml.Serialization.XmlSerializer(typeof(TestClass)); 
    sw.Stop(); 
    MessageBox.Show(sw.Elapsed.ToString()); 
} 

Così sto realtà non un'istanza di qualsiasi Forme più, solo test. TestClass è una piccola classe con solo tre proprietà pubbliche int e nient'altro. Il mio file .exe principale (Windows Form) è di circa 1 MB di larghezza, se questo fa alcuna differenza.

2. Risultati

in modalità debug, il mio tempo trascorso è ~ 200ms, mentre in uscita ci vuole ~ 1.2s.

3. Ulteriori informazioni

La cosa strana è quando provo a impostare qualche altro progetto in questa soluzione come progetto di avvio, perché in tal caso essa funziona veloce (esattamente lo stesso codice come sopra).

4. mod rapida

Per risolvere questo bug il più rapidamente possibile, ho creato un nuovo progetto di avvio exe nella mia soluzione, che crea un'istanza e gestisce il modulo di domanda principale facendo riferimento il mio primo progetto di ingresso. In tal caso funziona di nuovo veloce, il mio entry exe ora è solo 24kb di grandi dimensioni, contenente solo un metodo Main statico.

Qualcuno ha riscontrato un comportamento simile prima? Se mi fossi imbattuto in questo altrove, osservando il codice qui sopra, probabilmente presumerei che ci sia un inizializzatore statico da qualche parte, facendo tonnellate di lavoro in un thread separato (ma non è il caso qui, non ho questo roba), e inoltre eseguendo solo in Release build?

[Edit] Maggiori informazioni: Sono consapevole che XmlSerializer genera codice IL in fase di esecuzione, ma la mia domanda reale è perché funziona più lentamente, in questo caso che in altri casi. Quando eseguo il benchmark solo sulla serializzazione effettiva, è 3 volte più lento in Release (ma solo se lo eseguo dal mio progetto iniziale).

[Aggiornamento] Ora per la parte più strana in assoluto: dopo un paio di passaggi di modifica/ricostruzione, il mio nuovo progetto di inserimento ha iniziato a comportarsi come il primo: avvio lento, caricamento lento. Ho cambiato il nome del progetto e il GUID e lo ho ricostruito e funziona di nuovo velocemente.

+0

Considerare che XmlSerializer genera una classe in fase di esecuzione per gestire la serializzazione effettiva. Produce codice C# e lo compila in fase di esecuzione. –

+0

Lo capisco, ma non capisco perché è sempre più lento nella mia applicazione Release exe.Inoltre, posso istanziare XmlSerializer, dormire per 10 secondi, per esempio, e poi fare il vero timer di serializzazione 1000 a benchmark - ed è sempre più lento in Release. – Groo

risposta

6

Penso che questo sia dovuto al fatto che XmlSerializer fa funzionare NGEN al momento dell'avvio in modalità di rilascio, ma non in modalità di debug. Vedi per es.

http://blogs.msdn.com/billwert/archive/2008/02/23/use-of-sgen-exe-to-avoid-common-xmlserializer-performance-pitfalls.aspx

per alcuni dettagli.

+0

Grazie, ho effettivamente utilizzato SGEN per generare gli assembly di serializzazione in modalità di rilascio, ma è stato comunque più lento. È ancora più lento quando creo prima un serializzatore e poi contrassegno solo la serializzazione stessa. (a proposito, il tuo link lo mostra in mozilla: "il sito web all'indirizzo www.topxml.com è stato segnalato come sito di attacco") – Groo

+0

Sì, ricevi lo stesso avviso. Anche Google avverte di questo sito: http://www.google.de/search?hl=de&q=site%3Awww.topxml.com –

+0

Grazie, ho corretto l'url sul blog originale di msdn. – Brian

Problemi correlati