2009-07-14 11 views
1

I haben einen Test winforms app mit ThreadExceptionHandler dass ein Meldungsfeld angezeigt wird, wenn eine nicht behandelte Ausnahme gefangen wird, wie folgt:ThreadExceptionHandler Fang Ausnahme nicht in MainFrm Konstruktor

[STAThread] 
static void Main() 
{ 
    Application.ThreadException += new System.Threading.ThreadExceptionEventHandler(Application_ThreadException); 
    Application.EnableVisualStyles(); 
    Application.SetCompatibleTextRenderingDefault(false); 
    Application.Run(new Form1()); 
} 

static void Application_ThreadException(object sender, System.Threading.ThreadExceptionEventArgs e) 
{ 
    MessageBox.Show("error caught"); 
} 

Wenn ich erzwingen einen Fehler in der Ctor der Form 1 (zB DivideByZero) wie folgt:

public Form1() 
{ 
    InitializeComponent(); 

    int i = 0; 
    int x = 5/i; 
} 

und die App außerhalb von Visual Studio (in Windows 7) laufen, die Division durch Null Ausnahme ist nicht behandelt - ich bekomme ein wenig hilfreich „WindowsFormApplica tion1 hat aufgehört zu arbeiten ... "Nachricht.

Allerdings,, wenn ich die divebyzero Ausnahme auf das Form1_Load Ereignis verschieben und erneut ausführen, wird die Ausnahme ordnungsgemäß behandelt.

Kann jemand erklären, warum das der Fall ist? Der Grund, warum ich dieses Testprogramm ausgeführt habe, ist, dass ich ein ähnliches unbehandeltes Ausnahmeproblem in einer anderen Unternehmensanwendung erfahre, die ich aufzuspüren versuche.

Antwort

4

Dies liegt wahrscheinlich daran, dass der Konstruktor ausgeführt wird, bevor Application.Run() aufgerufen wird. Der Code könnte auch als

[STAThread] 
static void Main() 
{ 
    Application.ThreadException += new System.Threading.ThreadExceptionEventHandler(Application_ThreadException); 
    Application.EnableVisualStyles(); 
    Application.SetCompatibleTextRenderingDefault(false); 
    Form1 MyForm = new Form1(); 
    Application.Run(MyForm); 
} 

Handler Ihre Thread Ausnahme geschrieben werden nur aktiv wird, wenn Application.Run() ausgeführt wird. Um Ausnahmen im Formularkonstruktor abzufangen, müssen Sie Form1 MyForm = new Form1(); mit einem separaten try/catch-Block umgeben.

+0

+1 - Ihre klare Beschreibung schlägt meine ... :) –

3

Der Fehler wird im Konstruktor, nicht im Thread-Code geworfen. Ihr Code:

Application.Run(new Form1()); 

wird die Ausnahme dann und dort zu werfen, genau an diesem Codezeile vor dem Aufruf von Application.Run(), so dass die Gewinde Code nicht einmal ansatz ausführt.

1

ThreadException behandelt Ausnahmen Ausnahmen für Benutzeroberflächen-Threads. UnhandledException behandelt Nicht-UI-Thread-Ausnahmen.

Sie benötigen diese Zeile in Main() hinzufügen:

AppDomain.CurrentDomain.UnhandledException += new UnhandledExceptionEventHandler(CurrentDomain_UnhandledException); 

und die folgenden in der Klasse:

static void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e) 
{ 
    MessageBox.Show("error caught 2"); 
} 
0

Application.ThreadException Ereignis wird jedes Mal Anwendung löst eine Ausnahme genannt, In Ihrem Beispiel wird die Ausnahme jedoch im Hauptthread ausgelöst. Sie können dafür einen try catch-Block hinzufügen.

Verwandte Themen