继续嵌套的 while 循环

发布于 2024-07-27 12:54:57 字数 296 浏览 6 评论 0原文

在此代码示例中,是否有任何方法可以从 catch 块继续执行外循环?

while
{
   // outer loop

   while
   {
       // inner loop
       try
       {
           throw;
       }
       catch 
       {
           // how do I continue on the outer loop from here?
           continue;
       }
   }
}

In this code sample, is there any way to continue on the outer loop from the catch block?

while
{
   // outer loop

   while
   {
       // inner loop
       try
       {
           throw;
       }
       catch 
       {
           // how do I continue on the outer loop from here?
           continue;
       }
   }
}

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

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

发布评论

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

评论(11

悟红尘 2024-08-03 12:54:58

你只想打破内在,而内在却会延续外在。

while
{
   // outer loop

   while
   {
       // inner loop
       try
       {
           throw;
       }
       catch 
       {
           // how do I continue on the outer loop from here?
           break;
       }
   }
}

You just want to break from the inner which would continue the outer.

while
{
   // outer loop

   while
   {
       // inner loop
       try
       {
           throw;
       }
       catch 
       {
           // how do I continue on the outer loop from here?
           break;
       }
   }
}
如痴如狂 2024-08-03 12:54:58

如果您想使用 try catch,只需将它们向外移动(尽管我建议重构)。

只有当它是一个错误并且需要记录时我才会这样做,我也会推送

while
{
    try 
    {
        DoStuffToThisElement(item);
    }
    catch(Exception ex)
    {
        logError(ex);
    }
}

private void  DoStuffToThisElement(Item item)
{
    while
    {
        if(condition)
        {
            throw;
        }
    }
}

If you wish to use try catch, simply move them outwards (although I would recommend refactoring).

I would only do this if it IS an error and needs logging, I would also push

while
{
    try 
    {
        DoStuffToThisElement(item);
    }
    catch(Exception ex)
    {
        logError(ex);
    }
}

private void  DoStuffToThisElement(Item item)
{
    while
    {
        if(condition)
        {
            throw;
        }
    }
}
冷…雨湿花 2024-08-03 12:54:58

我认为实现此目的的最佳方法是使用 break 语句。 Break 结束当前循环从结束处继续执行。 在这种情况下,它将结束内部循环跳回外部 while 循环。 这就是您的代码的样子:

while
{
   // outer loop

   while
   {
       // inner loop
       try
       {
           throw;
       }
       catch 
       {
           // break jumps to outer loop, ends inner loop immediately.
           break; //THIS IS THE BREAK
       }
   }
}

我相信这就是您想要完成的,对吗?
谢谢!

I think the best way to accomplish this would be to use the break statement. Break ends the current loop and continues execution from where it ends. In this case, it would end the inner loop and jump back into the outer while loop. This is what your code would look like:

while
{
   // outer loop

   while
   {
       // inner loop
       try
       {
           throw;
       }
       catch 
       {
           // break jumps to outer loop, ends inner loop immediately.
           break; //THIS IS THE BREAK
       }
   }
}

I believe that is what you were looking to be accomplished, correct?
Thanks!

亣腦蒛氧 2024-08-03 12:54:58
using System;

namespace Examples
{

    public class Continue : Exception { }
    public class Break : Exception { }

    public class NestedLoop
    {
        static public void ContinueOnParentLoopLevel()
        {
            while(true)
            try {
               // outer loop

               while(true)
               {
                   // inner loop

                   try
                   {
                       throw new Exception("Bali mu mamata");
                   }
                   catch (Exception)
                   {
                       // how do I continue on the outer loop from here?

                       throw new Continue();
                   }
               }
            } catch (Continue) {
                   continue;
            }
        } 
    }

}

}
using System;

namespace Examples
{

    public class Continue : Exception { }
    public class Break : Exception { }

    public class NestedLoop
    {
        static public void ContinueOnParentLoopLevel()
        {
            while(true)
            try {
               // outer loop

               while(true)
               {
                   // inner loop

                   try
                   {
                       throw new Exception("Bali mu mamata");
                   }
                   catch (Exception)
                   {
                       // how do I continue on the outer loop from here?

                       throw new Continue();
                   }
               }
            } catch (Continue) {
                   continue;
            }
        } 
    }

}

}
尛丟丟 2024-08-03 12:54:58

使用自己的异常类型,例如 MyException。 然后:

while
{
   try {
   // outer loop
   while
   {
       // inner loop
       try
       {
           throw;
       }
       catch 
       {
           // how do I continue on the outer loop from here?
           throw MyException;
       }
   }
   } catch(MyException)
   { ; }
}

这将适用于继续和打破多层嵌套 while 语句。
抱歉,格式错误;)

Use an own exception type, e.g., MyException. Then:

while
{
   try {
   // outer loop
   while
   {
       // inner loop
       try
       {
           throw;
       }
       catch 
       {
           // how do I continue on the outer loop from here?
           throw MyException;
       }
   }
   } catch(MyException)
   { ; }
}

This will work for continuing and breaking out of several levels of nested while statements.
Sorry for bad formatting ;)

执手闯天涯 2024-08-03 12:54:57

更新:这个问题是我关于这个主题的文章的灵感。< /a> 感谢您提出这个好问题!


“继续”和“中断”只不过是“转到”的令人愉快的语法。 显然,通过给它们起可爱的名字并将它们的使用限制在特定的控制结构上,它们不再引起“所有的 goto 一直都是坏的”人群的愤怒。

如果您想要做的是继续到外部,您可以简单地在外部循环的顶部定义一个标签,然后“转到”该标签。 如果您认为这样做不会妨碍代码的可理解性,那么这可能是最方便的解决方案。

但是,我会以此为契机考虑您的控制流是否会从某些重构中受益。 每当我在嵌套循环中有条件“中断”和“继续”时,我就会考虑重构。

考虑:

successfulCandidate = null;
foreach(var candidate in candidates)
{
  foreach(var criterion in criteria)
  {
    if (!candidate.Meets(criterion))
    {  // TODO: no point in continuing checking criteria.
       // TODO: Somehow "continue" outer loop to check next candidate
    }
  }
  successfulCandidate = candidate;
  break;
}
if (successfulCandidate != null) // do something

两种重构技术:

第一,将内部循环提取到方法中:

foreach(var candidate in candidates)
{
  if (MeetsCriteria(candidate, criteria))
  { 
      successfulCandidate = candidate;
      break;
  }
}

第二,可以消除所有循环吗? 如果您因为尝试搜索某些内容而进行循环,请将其重构为查询。

var results = from candidate in candidates 
              where criteria.All(criterion=>candidate.Meets(criterion))
              select candidate;
var successfulCandidate = results.FirstOrDefault();
if (successfulCandidate != null)
{
  do something with the candidate
}

如果没有循环,则无需中断或继续!

UPDATE: This question was inspiration for my article on this subject. Thanks for the great question!


"continue" and "break" are nothing more than a pleasant syntax for a "goto". Apparently by giving them cute names and restricting their usages to particular control structures, they no longer draw the ire of the "all gotos are all bad all the time" crowd.

If what you want to do is a continue-to-outer, you could simply define a label at the top of the outer loop and then "goto" that label. If you felt that doing so did not impede the comprehensibility of the code, then that might be the most expedient solution.

However, I would take this as an opportunity to consider whether your control flow would benefit from some refactoring. Whenever I have conditional "break" and "continue" in nested loops, I consider refactoring.

Consider:

successfulCandidate = null;
foreach(var candidate in candidates)
{
  foreach(var criterion in criteria)
  {
    if (!candidate.Meets(criterion))
    {  // TODO: no point in continuing checking criteria.
       // TODO: Somehow "continue" outer loop to check next candidate
    }
  }
  successfulCandidate = candidate;
  break;
}
if (successfulCandidate != null) // do something

Two refactoring techniques:

First, extract the inner loop to a method:

foreach(var candidate in candidates)
{
  if (MeetsCriteria(candidate, criteria))
  { 
      successfulCandidate = candidate;
      break;
  }
}

Second, can all the loops be eliminated? If you are looping because you are trying to search for something, then refactor it into a query.

var results = from candidate in candidates 
              where criteria.All(criterion=>candidate.Meets(criterion))
              select candidate;
var successfulCandidate = results.FirstOrDefault();
if (successfulCandidate != null)
{
  do something with the candidate
}

If there are no loops then there is no need to break or continue!

浮云落日 2024-08-03 12:54:57
    while
    {
       // outer loop

       while
       {
           // inner loop
           try
           {
               throw;
           }
           catch 
           {
               // how do I continue on the outer loop from here?
               goto REPEAT;
           }
       }
       // end of outer loop
REPEAT: 
       // some statement or ; 
    }

问题解决了。 (什么?为什么你们都用那种肮脏的眼神看我?)

    while
    {
       // outer loop

       while
       {
           // inner loop
           try
           {
               throw;
           }
           catch 
           {
               // how do I continue on the outer loop from here?
               goto REPEAT;
           }
       }
       // end of outer loop
REPEAT: 
       // some statement or ; 
    }

Problem solved. (what?? Why are you all giving me that dirty look?)

沉默的熊 2024-08-03 12:54:57

你可以利用休息时间; 陈述。

while
{
   while
   {
       try
       {
           throw;
       }
       catch 
       {
           break;
       }
   }
}

continue 用于跳回到当前循环的顶部。

如果您需要突破更多级别,则必须添加某种“if”或使用可怕/不推荐的“goto”。

You can use a break; statement.

while
{
   while
   {
       try
       {
           throw;
       }
       catch 
       {
           break;
       }
   }
}

Continue is used to jump back to the top of the current loop.

If you need to break out more levels than that you will either have to add some kind of 'if' or use the dreaded/not recommended 'goto'.

眼趣 2024-08-03 12:54:57

将 try/catch 结构与内部 while 循环交换:

while {
  try {
    while {
      throw;
    }
  }
  catch {
    continue;
  }
}

Swap the try/catch structure with the inner while loop:

while {
  try {
    while {
      throw;
    }
  }
  catch {
    continue;
  }
}
心房的律动 2024-08-03 12:54:57

编号
我建议将内部循环提取到一个单独的方法中。

while
{
   // outer loop
       try
       {
           myMethodWithWhileLoopThatThrowsException()
       }
       catch 
       {
           // how do I continue on the outer loop from here?
           continue;
       }
   }
}

No.
I suggest, extracting the inner loop into a separate method.

while
{
   // outer loop
       try
       {
           myMethodWithWhileLoopThatThrowsException()
       }
       catch 
       {
           // how do I continue on the outer loop from here?
           continue;
       }
   }
}
苹果你个爱泡泡 2024-08-03 12:54:57

在内循环中使用break

Use break in the inner loop.

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