防止递归函数中出现 StackOverFlow

发布于 2024-10-14 14:08:13 字数 276 浏览 9 评论 0原文

我在 BaseClass 中有一个递归函数,它的返回条件依赖于 protected virtual 函数。

子类可能会错误地重写此函数并导致 StackOverFlow 异常。最糟糕的是有一些缓慢的网络调用,并且异常不会很快发生(许多资源浪费了很长一段时间)。

我正在寻找一种在基类中以某种方式在早期阶段检查 StackOverFlow 的方法(可能使用Reflection 和当前的递归级别)。

有什么想法吗?

I have a recursive function in a BaseClass which relies on a protected virtual function for it's return condition.

It's possible for a child class to override this function incorrectly and leads to a StackOverFlow exception. The worst thing is there are some slow network calls and the exception is not gonna happen soon (many resources waste for a long time).

I'm looking for a method to check StackOverFlow in early stages some way in the base class (maybe using Reflection and the current recursion level).

Any idea ?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

梦里的微风 2024-10-21 14:08:14

您可以将一个简单的整数“深度”传递给递归函数,并在每次后续调用时递增它。如果它大于允许的最大深度,则立即抛出异常,而不是等到为时已晚并且发生可怕的 StackOverflow 异常。

这种安全机制(增量计数器,检查它是否大得愚蠢)在 while 循环中也很方便,其中一个小错误可能会导致无限循环,消耗大量 CPU。

在拥有许多用户的大型系统(例如网站)中,有时最好采取诸如递归和 while 循环之类的预防措施,因为后果可能远远超出一个网页或系统的一个用户。这不是漂亮的代码,纯粹主义者无疑会犹豫不决,但它很高效,具有防御性,而且很实用。

You could pass a simple integer 'depth' to the recursive function and increment it with each subsequent call. If it gets larger than the maximum allowed depth throw an Exception right then instead of waiting until it's too late and the dreaded StackOverflow exception has occurred.

Such safety mechanisms (increment counter, check it's not stupidly large) can also be handy in while loops where a small error can cause an infinite loop consuming vast quantities of CPU.

In large systems with many users (e.g. web sites) sometimes it's best to take precautionary measures like these with recursion and while loops because the consequences can reach far beyond one web page or one user of the system. It's not pretty code and the purists will no doubt balk at it, but it's efficient, it's defensive and it's pragmatic.

奢望 2024-10-21 14:08:14

解决问题而不是创建解决方法。创建一个递归的私有函数,该函数调用受保护的虚函数。

Solve the problem instead of creating a workaround. Create a private function which is recursive which calls the protected virtual function.

通知家属抬走 2024-10-21 14:08:14

尽管您可能可以阅读调用堆栈并对其进行分析,但我不会这样做。

  1. 它将减慢执行速度
  2. 这不是您的基类的责任
  3. 记录您的基类的行为

另一种方法是仅在调试模式下进行调用堆栈分析。这是一些代码来了解如何获取调用堆栈。

using System.Diagnostics;

[STAThread]
public static void Main()
{
  StackTrace stackTrace = new StackTrace();           // get call stack
  StackFrame[] stackFrames = stackTrace.GetFrames();  // get method calls (frames)

  // write call stack method names
  foreach (StackFrame stackFrame in stackFrames)
  {
    Console.WriteLine(stackFrame.GetMethod().Name);   // write method name
  }
}

来自此网站

Although you probably can read the call stack and analyze it I wouldn't do that.

  1. It will slow down execution
  2. It is not your base class' responsibility
  3. Document your base class' behaviour

An alternative could be to do the call stack analysis in DEBUG mode only. Here is a little code to see how to get the call stack.

using System.Diagnostics;

[STAThread]
public static void Main()
{
  StackTrace stackTrace = new StackTrace();           // get call stack
  StackFrame[] stackFrames = stackTrace.GetFrames();  // get method calls (frames)

  // write call stack method names
  foreach (StackFrame stackFrame in stackFrames)
  {
    Console.WriteLine(stackFrame.GetMethod().Name);   // write method name
  }
}

From this site

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文