2011-05-09 36 views
6

He creado una nueva aplicación WPF y añadido un controlador de eventos para el evento cargado en MainWindow:WPF: Una aplicación no se cae si se produce una excepción en el evento Loaded

Loaded += (s, e) => { throw new Exception("AAAA!"); }; 

entonces comienzo esta aplicación de Visual C# y la aplicación no falla ni muestra una excepción no detectada.

Espero que se bloquee y esta aplicación se bloquee en otras computadoras. Pero, ¿por qué funciona en el mío?

actualización ha añadido una captura de pantalla: screenshot

+2

¿Porque la aplicación está compilada para "Cualquier CPU" y está ejecutando un sistema operativo de 64 bits? –

+0

@Cody Gray fue compilado para x86 y estoy ejecutando un sistema operativo de 64 bits. Se cambió a "Cualquier CPU" y la aplicación se bloqueó. Interesante. – meze

+0

Argh, jugué con 'Thread.Sleep' y ahora no se bloquea si está compilado para" Cualquier CPU ". – meze

Respuesta

4

El evento Loaded además probablemente se llama desde un subproceso en segundo plano. Cuando se lanza una excepción en este hilo, se terminará, pero no afectará a la secuencia principal de la aplicación. Este comportamiento se puede ver en muchos controladores de eventos, p. un controlador de eventos Timer_Elapsed tampoco afectará su código en general. ¡Esto no significa que no debería preocuparse por las excepciones dentro de dicho código!

+0

¿Cómo puedo verificar eso? Agregué 'Thread.Sleep (1000)' antes de lanzar una excepción y toda la ventana se bloquea durante 1 segundo. Así que espero que estén en el mismo hilo. – meze

+0

podría intentar copear Thread.Actualmente con this.Dispatcher.Thread para detectar esto y/o comprobar el resultado de esto.Dispatcher.CheckAccess(). Pero tal vez no es necesario, ¿qué es lo que quieres lograr? (FU'2 las respuestas y los comentarios sobre los míos, esos parecen estar en el mismo camino ...) – eFloh

+2

Como desarrollador, quiero que mi aplicación falle si no he detectado todas las excepciones. No quiero que mi aplicación siga funcionando cuando algo se rompe. Tampoco entiendo por qué 'Loaded' se activará en otro hilo. Acabo de probar esto: 'Loaded + = (s, e) => {if (this.Dispatcher.Thread.Equals (Thread.CurrentThread)) Thread.Sleep (4000); lanzar nueva Excepción ("AAAA!"); }; '. La ventana se congela durante 4 segundos y luego todo está bien, ningún diálogo "esta aplicación ha dejado de funcionar". – meze

6

Para detectar la excepción, debe intentar/atrapar en el método Loaded, o puede decirle al Dispatcher que le avise cuando ocurra una excepción no controlada.

intente lo siguiente, por ejemplo, en el método OnStartup de su aplicación:

App.Current.DispatcherUnhandledException += (s,e) => 
{ 
    // Handle the exception here 
    var ex = e.Exception; 
}; 

Editar:

Si desea que la aplicación se bloquee a continuación, intente lo siguiente:

App.Current.DispatcherUnhandledException += (s,e) => 
{ 
    // this should cause your application to crash :-) 
    throw new Exception("Now it should crash!", e.Exception); 
}; 

La diferencia aquí es que creamos una nueva excepción que se lanza en el hilo de la interfaz de usuario.

+0

Sí, lo sé.Pero ¿por qué no veo el diálogo estándar de Windows "La aplicación ha dejado de funcionar" cuando no tengo 'DispatcherUnhandledException'? – meze

+0

Si espera que su aplicación se bloquee, la excepción debe aparecer en el hilo de la interfaz de usuario. Intente generar una nueva excepción dentro del manejador de excepciones. –

+0

@meze: actualicé mi respuesta con una versión que falla :-) –

Cuestiones relacionadas