426

采取以下功能:

DataTable go() {
    return someTableAdapter.getSomeData();
}

当我在这个函数中设置断点时,是否有可能检查返回值?go()直接耦合到.aspx页面中的数据网格。

检查返回的数据表的唯一方法是使用临时变量。但是,这有点不方便。难道没有别的办法了吗?

4

21 回答 21

301

从来没听说过。请注意,如果您确实添加了一个变量,无论如何它都会在发布版本中被编译器删除......

更新: 此功能已添加到 VS2013中。您可以在自动窗口中查看返回值或$ReturnValue在监视/立即窗口中使用。

该值只能在从函数返回后直接看到,因此访问它的最简单方法是在函数调用上放置一个断点并跳过 (F10) 调用。


VS2015 更新:嘘!不幸的是,它似乎不在 VS2015 (devenv v14)
VS2017 更新中:它回来了。(devenv v15)

于 2008-11-06T09:26:00.050 回答
57

这可以根据客户反馈站点在带有 CLR 4.5.1 的 Visual Studio 2013 中完成。它在 C# 的早期版本中不可用。

(Visual Studio 2008 和更早的版本支持 VB.NET。它一直可供 C/C++ 开发人员使用。)

于 2010-09-15T05:25:26.390 回答
26

我同意这是一件非常有用的事情:不仅可以在退出之前查看方法的返回值,还可以查看我刚刚跨过的方法的返回值。我将它作为 Visual Studio 商业扩展的一部分实现,称为“ OzCode ”。

有了它,您可以直接在代码编辑器上查看方法返回值,就像 HUD 显示一样:

报表可视化

欲了解更多信息,请观看此视频

于 2011-11-18T09:49:26.257 回答
23

根据微软的说法,没有办法通过托管代码可靠地实现这一点。这是他们意识到并正在解决的问题:

对于那些有调试本机 C++ 或 VB6 代码经验的人,您可能已经使用了在“自动”窗口中为您提供函数返回值的功能。不幸的是,托管代码不存在此功能。虽然您可以通过将返回值分配给局部变量来解决此问题,但这并不方便,因为它需要修改您的代码。在托管代码中,确定您已跨过的函数的返回值要复杂得多。我们意识到我们无法在这里始终如一地做正确的事情,因此我们删除了该功能,而不是在调试器中为您提供不正确的结果。但是,我们希望为您带来这一点,我们的 CLR 和调试器团队正在寻找一些潜在的解决方案来解决这个问题。不幸的是,这不是 Visual Studio 11 的一部分。

https://connect.microsoft.com/VisualStudio/feedback/details/597933/add-a-return-pseudo-variable-to-the-visual-studio-debugger-for-net-code

于 2012-06-17T14:33:15.523 回答
22

关于 Visual Studio 2015:

根据 Marc Gravell 目前接受的答案:

功能已添加到 Visual Studio 2013中。您可以在自动窗口中查看返回值或在监视/立即窗口中使用 $ReturnValue

该答案还表明此功能在 Visual Studio 2015 中不起作用。这不是(完全)正确的。在检查方法调用的返回值时,有以下注释:

您必须打开旧版表达式求值器才能识别$ReturnValue (工具/选项/调试/使用旧版 C# 和 VB 表达式求值器)。否则,您可以使用$ReturnValue1

我在 Visual Studio 2015 Enterprise 中对此进行了测试:

  • 关闭旧式表达式评估器:只有 $ReturnValue1有效
  • 打开旧式表达式求值器:$ReturnValue$ReturnValue1 有效
于 2016-03-18T10:01:58.750 回答
13

如果您转到菜单工具选项,IntelliTrace,并更改设置以收集事件和呼叫信息。

您可以返回到上一个调用事件 ( Ctrl++ Shift) F11,并在 autos 窗口中查看从方法调用返回的临时值作为方法名称的子项。

这不会向您显示您所在方法的返回值。它只是向您显示当前方法中调用的最后一个方法的返回值。

所以,这很好

DataTable go(){return someTableAdapter.getSomeData();}

因为它向您显示了someTableAdapter.getSomeData().

但不适用于:

int go(){return 100 * 99;}
于 2011-03-29T13:18:58.680 回答
12

.NET 之前的老技巧:打开 Registers 窗口并查看 EAX 寄存器的值。这包含最后调用的函数的返回值。

于 2012-10-30T04:06:04.877 回答
11

使用 Shift-F11 退出 go() 方法,然后在“Autos”调试窗口中,它将显示刚刚从堆栈中弹出的方法调用的返回值(在这种情况下,go() 方法是你想要什么)。这是 Visual Studio 2005 中的行为;我没有使用过 Visual Studio 2008,所以我不知道这在那个版本中的行为是否相同。

于 2008-11-06T09:53:04.457 回答
7

是的,有一个非常好的方法。一个显着的缺点是您必须等待 5 年,甚至 6 年。既然我看到你在 2008 年 11 月发帖,我建议你 waaaaaa...

……啊啊啊。瞧!只是为了您,MS 发布了最新的Visual Studio 2013 ,它是在调试模式下运行时可从菜单访问的默认功能(菜单DebugWindowsAutos)。

于 2014-09-03T12:29:53.267 回答
5

有很多解决方法,但似乎没有一个令人满意。

引用下面的 John Skeet(评论现已删除的答案):

对我来说仍然看起来很不方便 - 特别是如果您在开始调试之前不知道需要哪个返回值。我真的不想每次我返回任何东西时都需要一个临时变量来弄乱我的代码。t

理论上,调试器可以有一个 -return变量。毕竟:它只是堆栈上的一个变量:

unsafe {
  int * sp = stackalloc int[1];
  try {
    return a+b;
  }
  finally {
    Trace.WriteLine("return is " + *(sp+3));
  }
}

因此,请将此视为 Visual Studio 的功能请求。

于 2009-02-09T08:17:42.857 回答
5

我想扩展PascalK 的答案,以使其在 Visual Studio 2015 中工作,因为有一个隐藏功能未在检查方法调用的返回值中记录。

如果您有嵌套函数调用,则会自动创建伪变量$ResultValueX,其中 X 指的是函数调用顺序。因此,如果您有诸如 的调用Multiply(Five(), Six()),则会创建以下伪变量:

Five()     | $ResultValue1 = 5
Six()      | $ResultValue2 = 6
Multiply() | $ResultValue3 = 30
于 2016-05-31T22:21:05.870 回答
2

我知道的唯一方法是在返回行上放置一个断点,然后调用Quick Watch窗口并输入返回的表达式:

someTableAdapter.getSomeData();

但这仅在调用不更改任何对象的状态时才有效(因为当您恢复执行时,将对同一方法进行第二次调用)。

于 2009-01-19T06:00:28.160 回答
2

Microsoft Visual C++ 曾经这样做,但 Visual Studio 没有 AFAIK.. :(

于 2010-06-16T10:52:41.840 回答
1

您也可以要求评估中间窗口中的值,如果它没有设置标志或其他变量,而只是返回一些东西。

于 2008-11-06T09:42:39.547 回答
1

打开 Debug → Autos 窗口会让你关闭。它不会显示实际的返回值,但会显示在 return 语句中评估的内容。

于 2008-11-06T09:58:01.763 回答
1

我认为您可以通过查看 Registers 窗口(Debug / Windows / Registers)中的 RAX 寄存器来确定这一点。退出函数(SHIFT + F11)后,检查RAX寄存器。我不知道事实,但有一次你可以检查一个寄存器(.NET 之前的日子)并在那里查看返回值。它甚至可能是 RAX 和 RBX 等的组合。

于 2013-07-11T20:48:28.173 回答
1

是的,通过切换到 VB.NET。;P(你刚才说的是“Visual Studio”。;)

只要我记得(从 Visual Basic 到 VB.NET 的所有版本),您就可以简单地查询函数名称。Exit Function它像在函数开始时隐式声明的局部变量一样“起作用”,并且每当函数通过非返回语句退出时(即或只是失败),它的当前值也用作返回值,当然,当使用 return 语句。

它也被设置为 return 语句的表达式。就像局部变量一样,它的值可以在函数内部的任何执行点检查(包括在执行 return 语句之后)。C# 没有这个并且应该。

这个小小的 VB.NET 特性(加上Exit Function它启用的语句 - C# 没有并且应该的另一个特性)在我练习的一种防御性编程形式中非常有用,我总是将函数名称初始化为失败/默认值作为第一个声明。然后,在任何失败点(通常比成功点更频繁地发生),我可以简单地调用该Exit Function语句(即不必复制失败/默认表达式甚至常量/变量名称)。

于 2014-07-19T00:56:48.330 回答
1

接受的答案不适用于 Visual Studio 2015,但通过在方法的最后一行放置一个断点并按F10,它会将返回值的所有表达式放入本地窗口。

于 2016-07-19T12:21:44.630 回答
0

您可以尝试选择"someTableAdapter.getSomeData();",右键单击它,然后选择Quick Watch

于 2008-11-06T09:27:47.813 回答
0

将返回表达式拖放到监视窗口中。

例如,在声明中

return someTableAdapter.getSomeData();

拖放

someTableAdapter.getSomeData()

进入监视窗口,您将看到该值。

您可以对任何表达式执行此操作。

于 2009-02-09T01:18:22.973 回答
0

在 VS2019 中,只需转到 Debug->Windows->Autos 窗口。在那里,您会看到 concat 返回值,如下所示:

在此处输入图像描述

于 2021-12-29T12:14:53.070 回答