2008-10-01 8 views
153

¿Hay alguna forma de colocar un reloj en la variable y solo se puede interrumpir Visual Studio cuando ese valor cambia?Interrumpir cuando un valor cambia con el depurador de Visual Studio

Haría mucho más fácil encontrar problemas de estado difíciles.

¿Se puede hacer esto?

Las condiciones de punto de interrupción aún necesitan un conjunto de puntos de interrupción, y prefiero establecer un reloj y dejar que Visual Studio establezca los puntos de interrupción en los cambios de estado.

+0

pero el punto de interrupción no afecta nada a menos que la condición se mantenga, por lo que puede poner su punto de interrupción en cualquier lugar (como el Setter) y tomar desde allí. ¿O me estoy perdiendo algo? – Oskar

+6

bien. es como la forma vb6 de depuración. no te importa la ubicación del punto de interrupción. solo agregue una expresión condicional para ver la ventana y vb6 garantizará que se romperá donde sea que se cumpla la condición. –

+0

lo siento, nunca he visto una manera, hasta donde sé, el colocador es el camino a seguir – Oskar

Respuesta

96

En el Visual Studio 2005 menú:

depuración ->Nuevo punto de interrupción ->Nuevos datos de punto de interrupción

Introduzca:

&myVariable 
+28

¿está disponible para código administrado? Veo esta opción deshabilitada para el proyecto C#. Recuerde leer en alguna parte esta es una característica difícil de implementar en la depuración de aplicaciones administradas, especialmente con el recolector de basura involucrado. –

+15

Desafortunadamente, solo está disponible para código no administrado: http://msdn.microsoft.com/en-us/library/350dyxd0.aspx –

+1

Creo que todavía necesita poner un punto de interrupción si sus datos no son globales. VS reemplaza la & var por la dirección de memoria, no recuerda entre las ejecuciones que le gustaría detener en esta variable. – nus

2

El clic derecho en el punto de interrupción funciona bien para mí (aunque principalmente lo estoy usando para puntos de corte condicional en valores de variables específicos. Incluso funciona romper expresiones que implican un nombre de subproceso que es muy útil si está tratando de detectar problemas de subprocesamiento)

1

Se puede utilizar un punto de observación de memoria en código no administrado. Sin embargo, no estoy seguro de si están disponibles en el código administrado.

22

También puede optar por romper explícitamente en el código:

// Assuming C# 
if (condition) 
{ 
    System.Diagnostics.Debugger.Break(); 
} 

De MSDN:

Debugger.Break: Si ningún depurador asociado, los usuarios son preguntó si desean adjuntar un depurador . En caso afirmativo, el depurador es iniciado. Si un depurador asociado, el depurador se señaliza con un evento de punto de interrupción de usuario y el depurador suspende la ejecución del proceso que se acaba como si un punto de interrupción depurador había sido éxito.

Esto es solo un retroceso, sin embargo. Establecer un punto de interrupción condicional en Visual Studio, como se describe en otros comentarios, es una mejor opción.

+2

FWIW, con editar y continuar Prefiero hacerlo de esta manera: IME, los puntos de interrupción condicionales son sloow –

+0

Esto funciona, pero es muy doloroso, terminé haciendo algo similar. Puse este en la parte superior de cada método que sospechaba -y de nuevo en la parte inferior (en una cláusula final) - de esa manera sabía exactamente qué método causaba el problema - (es decir, sabía que los datos eran buenos antes de ingresar el método, y luego mal antes de salir de ella). – BrainSlugs83

11

Imagine que tiene una clase llamada A con la siguiente declaración.

class A 
{ 
    public: 
     A(); 

    private: 
     int m_value; 
}; 

Quiere que el programa se detenga cuando alguien modifica el valor de "m_value".

Ir a la definición de clase y poner un punto de interrupción en el constructor de A.

A::A() 
{ 
    ... // set breakpoint here 
} 

Una vez dejamos el programa:

Depuración -> Nuevo punto de interrupción -> Nuevo punto de interrupción de datos ...

Dirección: & (this-> m_Value)
Byte Count: 4 (Porque int tiene 4 bytes)

Ahora, podemos reanudar el programa. El depurador se detendrá cuando se cambie el valor.

Puede hacer lo mismo con clases heredadas o clases compuestas.

class B 
{ 
    private: 
     A m_a; 
}; 

Dirección: & (this-> m_a.m_value)

Si no conoce el número de bytes de la variable que desea inspeccionar, se puede utilizar el operador sizeof.

Por ejemplo:

// to know the size of the word processor, 
// if you want to inspect a pointer. 
int wordTam = sizeof (void*); 

Si nos fijamos en la "pila de llamadas" se puede ver la función que cambia el valor de la variable.

+1

Entonces, ¿qué harías exactamente si lo que estoy buscando no está en mis propias clases? Como, por ejemplo, estoy tratando de averiguar exactamente dónde se activa o desactiva un control. Puedo agregar un reloj en el valor Habilitado del control durante la depuración, claro, pero no hay forma de romper el cambio y luego ver dónde se detuvo. – Nyerguds

+2

Si intenta depurar una biblioteca externa, necesitaría la biblioteca compilada en modo de depuración. No estoy familiarizado con el componente, pero tal vez pueda conectar una "devolución de llamada" a la propiedad y poner un punto de interrupción dentro. El formulario que describo necesita la dirección de la memoria, si no tiene forma de saberlo, debe buscar otros métodos. – momboco

1

Probablemente pueda hacer un uso inteligente de la función DebugBreak().

+0

¿Cómo exactamente? Al ejecutar un hilo separado en un ciclo cerrado e invocar a DebugBreak() cada vez que se ha encontrado un cambio? – nalply

+0

@nalpy Por ejemplo, podría rastrear los lugares donde 'myVariable' se usa y almacenar sus valores después de su uso en una variable auxiliar' previousValue', luego llamar a DebugBreak() cuando 'myVariable! = PreviousValue'; entonces sabría entre qué bloques de código 'myVariable' ha cambiado. Pero estoy de acuerdo con que la solución de AShelly es la mejor. – wil

3

Si está utilizando WPF, hay una herramienta increíble: WPF Inspector.
Se adjunta a una aplicación WPF y muestra el árbol completo de controles con todas las propiedades, y le permite (entre otras cosas) romper cualquier cambio de propiedad.

Pero lamentablemente no encontré ninguna herramienta que le permita hacer lo mismo con CUALQUIER propiedad o variable.

9

Cambie la variable en una propiedad y agregue un punto de interrupción en el método set. Ejemplo:

private bool m_Var = false; 
protected bool var 
{ 
    get { 
     return m_var; 
    } 

    set { 
     m_var = value; 
    } 
} 
0

Opcionalmente puede sobrecargar el operador = para la variable y puede poner el punto de interrupción dentro de la función sobrecargada en una condición específica.

15

realmente viejo puesto, pero en caso de que alguien no se da cuenta ...

En Visual Studio 2015, se puede colocar un punto de interrupción en el set de acceso de una propiedad Implementado-Auto y el depurador se interrumpirá cuando la propiedad se actualiza

public bool IsUpdated 
{ 
    get; 
    set; //set breakpoint on this line 
} 

actualización

alternativa; @AbdulRaufMujahid ha señalado en los comentarios que si la propiedad implementada automáticamente está en una sola línea, puede colocar el cursor en get; o y presionar F9 y se colocará un punto de interrupción en consecuencia. ¡Bonito!

public bool IsUpdated { get; set; } 
+3

Incluso si la propiedad implementada automáticamente está en una línea, p. cadena pública UserName {set; obtener; }. El usuario puede resaltar getter o setter y puede presionar F9 para agregar el breakpoint –

+0

@AbdulRaufMujahid Awesome! – Craig

Cuestiones relacionadas