在 Objective-C 中,finally 中的代码在返回后是否会运行?

发布于 2024-09-03 17:56:47 字数 326 浏览 13 评论 0原文

考虑以下代码:

@try {
  if (something.notvalid)
  {
    return;
  }
  // do something else
} @catch (NSException *ex) {
  // handle exception
} @finally {
  NSLog(@"finally!");
}

如果 something 无效并且我从 try 中返回,则 @finally 中的代码是否执行?我相信应该如此,但与我交谈过的其他人并不这么认为,而且我目前无法对此进行测试。

Consider the following code:

@try {
  if (something.notvalid)
  {
    return;
  }
  // do something else
} @catch (NSException *ex) {
  // handle exception
} @finally {
  NSLog(@"finally!");
}

If something is not valid and I return from within the try, does the code in @finally execute or not? I believe that it should but others I've spoken to don't think so and I'm unable to test this at the moment.

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

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

发布评论

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

评论(5

负佳期 2024-09-10 17:56:47

@finally 代码始终根据此处 和此处

@finally 块包含的代码
是否有异常都必须执行
是否抛出。

@finally code always executes according to here and here.

A @finally block contains code that
must be executed whether an exception
is thrown or not.

画尸师 2024-09-10 17:56:47

是的。奇怪的是,确实如此。我不知道为什么,但我只是构建了一个测试并尝试了多种配置,每次都如此。

配置如下:

  • 在try块中返回:停止try块的执行并导致finally执行
  • 在try块中返回并在finally中返回:停止try的执行并在finally块和整个方法中停止执行。
  • 在finally 块中返回:功能类似于try/catch/finally 块之外的正常返回。

Yes. Oddly enough, it does. I'm not sure why, but I just built a test and tried a number of configurations and every time it did.

Here were the configs:

  • Return in try block: stopped execution of try block and caused finally to be executed
  • Return in try block and return in finally: stopped execution of try and stopped execution in finally block and the entire method.
  • Return in finally block: functioned like normal return outside of a try/catch/finally block.
怕倦 2024-09-10 17:56:47

通过 RAI 定义,对于特定资源,Finally 块无论如何都会在该代码范围内执行。

它与Object的~Destructor含义相近。就像对象的 ~Destructor 总是执行一样,finally 块也会执行。

With the RAI definition, Finally block will anyhow executed with that code scope, for particular resource.

It has a close meaning with Object's ~Destructor. As same as an object's ~Destructor always executes, finally block also executes.

相思碎 2024-09-10 17:56:47

是的。即使在catch块中出现Exceptionfinally也会被执行。

如果您熟悉 C++,只需将 finally 视为 对象析构函数。无论对象内的语句处于什么状态,~Destructor 都将被执行。
但是你不能将 return 放在 finally 中[尽管有些编译器允许]。

请参阅下面的代码:查看全局变量 y 是如何更改的。
另请参阅 Exception1 如何被 Exception2 覆盖。

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace finallyTest
{
    class Program
    {
        static int y = 0;
        static int testFinally()
        {
            int x = 0;
            try
            {
                x = 1;
                throw new Exception("Exception1");
                x = 2;
                return x;
            }
            catch (Exception e)
            {
                x = -1;
                throw new Exception("Exception2", e);
            }
            finally
            {
                x = 3;
                y = 1;
            }
            return x;
        }

        static void Main(string[] args)
        {
            try
            {
                Console.WriteLine(">>>>>" + testFinally());
            }
            catch (Exception e)
            { Console.WriteLine(">>>>>" + e.ToString()); }
            Console.WriteLine(">>>>>" + y);
            Console.ReadLine();
        }
    }
}

输出:

    >>>>>System.Exception: Exception2 ---> System.Exception: Exception1
   at finallyTest.Program.testFinally() in \Projects\finallyTest\finallyTest\Program.cs:line 17
   --- End of inner exception stack trace ---
   at finallyTest.Program.testFinally() in \Projects\finallyTest\finallyTest\Program.cs:line 24
   at finallyTest.Program.Main(String[] args) in \Projects\finallyTest\finallyTest\Program.cs:line 38
>>>>>1

Yes. Even if there was an Exception within catch block, finally will be executed.

If you are familiar with C++, just think finally as the destructor of an object. What ever the state of a statement within the object, ~Destructor will be executed.
But you cant put return within finally[some compilers allow though].

See the code below: See how global variable y been changed.
Also see how Exception1 been covered by Exception2.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace finallyTest
{
    class Program
    {
        static int y = 0;
        static int testFinally()
        {
            int x = 0;
            try
            {
                x = 1;
                throw new Exception("Exception1");
                x = 2;
                return x;
            }
            catch (Exception e)
            {
                x = -1;
                throw new Exception("Exception2", e);
            }
            finally
            {
                x = 3;
                y = 1;
            }
            return x;
        }

        static void Main(string[] args)
        {
            try
            {
                Console.WriteLine(">>>>>" + testFinally());
            }
            catch (Exception e)
            { Console.WriteLine(">>>>>" + e.ToString()); }
            Console.WriteLine(">>>>>" + y);
            Console.ReadLine();
        }
    }
}

output:

    >>>>>System.Exception: Exception2 ---> System.Exception: Exception1
   at finallyTest.Program.testFinally() in \Projects\finallyTest\finallyTest\Program.cs:line 17
   --- End of inner exception stack trace ---
   at finallyTest.Program.testFinally() in \Projects\finallyTest\finallyTest\Program.cs:line 24
   at finallyTest.Program.Main(String[] args) in \Projects\finallyTest\finallyTest\Program.cs:line 38
>>>>>1
半世晨晓 2024-09-10 17:56:47

是的,这是一个示例片段,输出是

try!
抓住!
最后!

@try {
    NSLog(@"try!");

    NSException *e = [NSException
                      exceptionWithName:@"No Name"
                      reason:@"No Reason"
                      userInfo:nil];
    @throw e;


} @ catch (...)
{
    NSLog(@"catch!");
    return;
}
@finally
{
    NSLog(@"finally!");
}

NSLog (@"other code");

Yes, here is a sample snippet, the output is

try!
catch!
finally!

@try {
    NSLog(@"try!");

    NSException *e = [NSException
                      exceptionWithName:@"No Name"
                      reason:@"No Reason"
                      userInfo:nil];
    @throw e;


} @ catch (...)
{
    NSLog(@"catch!");
    return;
}
@finally
{
    NSLog(@"finally!");
}

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