如何在VS2015中的断点的条件表达式中使用Environment.StackTrace

时间:2016-07-07 13:03:52

标签: c# debugging visual-studio-2015 conditional-breakpoint

我正在尝试调试一个问题,如果我可以在一个属性的getter中有一个断点,那真的会有所帮助,但是每次从CanExecute调用中调用某个按钮时我都不需要中断我的UI。我的想法是我可以简单地调整不包含该字符串的调用堆栈上的断点,但这似乎不起作用。我能想到解释这个问题的最好方法是使用设置图像和断点输出。

BreakpointSettings

正如您在图像中看到的那样,断点的条件设置在被击中时直接输出,在输出中您可以看到它被正确击中几次.get(): true。然而,当它采用这个屏幕截图时,它的条件是假的,如输出中所示。该程序在断点被击中时停止,不正确。

我做错了什么 - 这有可能吗?对我来说就像VS2015中的一个错误,输出可以正确评估bool,为什么断点条件不能这样做呢?

编辑,以便在图像丢失时注释图像。 我在一个属性的get方法中有一个断点,它只返回底层字段。断点设置显示断点上有一个条件定义它,使得它只应在表达式!Environment.StackTrace.Contains("CanExecute")返回true时才被命中,即只有在堆栈跟踪不包含“CanExecute”字符串时才会中断。 断点设置的Action部分只使用$FUNCTION: {!Environment.StackTrace.Contains("CanExecute")}输出函数名称和条件表达式。该操作设置为不继续执行。

1 个答案:

答案 0 :(得分:1)

我不完全知道为什么在断点条件下无法使用堆栈跟踪信息,但是您可以通过疯狂的解决方法/黑客来扩展another answer

中概述的技术。

如果您使用自动属性,它将无法作为“干净”地使用,因为它需要两个断点,并且自动属性只有一个点可以将断点绑定到该点,但是我想这不是无论如何对于汽车财产还是有用的。


将第一个断点放在get方法的开头大括号上(将光标置于大括号上并按F9键)。在此断点上设置一个动作;将"Log a message to Output Window:"设置为

{System.AppDomain.CurrentDomain.SetData("break", !Environment.StackTrace.Contains("CanExecute"))}

并确保选中Continue execution

将第二个断点放在return语句上(将光标放在花括号上,然后按F9键)。在此断点上设置条件:

(bool)System.AppDomain.CurrentDomain.GetData("break")

取决于格式,在花括号和Debug > Windows > Breakpoints (Ctrl+Alt+B)语句在同一行的情况下,可能需要借助“断点”窗口return。您可以通过右键单击“断点”窗口中的断点并选择Settings

来编辑操作/条件。

强制转换为bool是因为GetData()返回object,而条件断点将无法为您转换。


它不是很漂亮,由于全局状态,它在多线程环境中不能很好地工作,但在紧要关头可能很有用。如果您需要这种方式的多个“条件断点”,请确保在SetData()/GetData()中使用其他密钥。

但是,如果可以的话,通常(取决于您的编译时间以及对代码和调试符号的访问权限)可以更快/更轻松地临时编辑代码以放置要打破的条件。

例如

public Foo Selected
{
    get
    {
        if (!Environment.StackTrace.Contains("CanExecute"))
            System.Diagnostics.Debugger.Break();

        return _selected;
    }
}

*对于自动属性,可以在CanExecute()方法中使用一对动作断点,在属性访问之前将“ break”设置为true,然后将“ break”设置为false,并用于条件

(bool?)System.AppDomain.CurrentDomain.GetData("break") != false

确保它在CanExecute()之前和之后仍然中断,而在此期间不会中断。