标签: finally

Java尝试最终的变化

这个问题困扰了我一段时间,但我还没有找到完整的答案(例如,这个是C#在try/finally之外或之内初始化一次性资源).考虑以下两个Java代码片段:

Closeable in = new FileInputStream("data.txt");
try {
    doSomething(in);
} finally {
    in.close();
}
Run Code Online (Sandbox Code Playgroud)

和第二种变化

Closeable in = null;
try {
    in = new FileInputStream("data.txt");
    doSomething(in);
} finally {
    if (null != in) in.close();
}
Run Code Online (Sandbox Code Playgroud)

令我担心的部分是线程可能在获取资源的时刻(例如文件被打开)之间有些中断,但结果值未分配给相应的局部变量.是否还有其他情况,线程可能会在上述点之外被中断,除了:

  1. 抛出InterruptedException(例如,通过Thread#interrupt())或抛出OutOfMemoryError异常
  2. JVM退出(例如通过kill,System.exit())
  3. 硬件失败(或JVM中的错误完整列表:)

我已经读到第二种方法有点"惯用",但IMO在上面的场景中没有区别,在所有其他场景中它们都是平等的.

所以问题是:

两者有什么不同?如果我担心释放资源(特别是在多线程应用程序中),我应该更喜欢哪个?为什么?

如果有人指出我支持答案的Java/JVM规范的部分,我将不胜感激.

java resources exception finally try-catch

5
推荐指数
2
解决办法
892
查看次数

理解'finally'块

我写了七个测试用例来理解finally块的行为.如何finally运作背后的逻辑是什么?

package core;

public class Test {
    public static void main(String[] args) {
        new Test().testFinally();
    }

    public void testFinally() {
        System.out.println("One = " + tryOne());
        System.out.println("Two = " + tryTwo());
        System.out.println("Three = " + tryThree());
        System.out.println("Four = " + tryFour());
        System.out.println("Five = " + tryFive());
        System.out.println("Six = " + trySix());
        System.out.println("Seven = " + trySeven());
    }

    protected StringBuilder tryOne() {
        StringBuilder builder = new StringBuilder();
        try {
            builder.append("Cool");
            return builder.append("Return");
        }
        finally {
            builder = null; …
Run Code Online (Sandbox Code Playgroud)

java finally try-finally

5
推荐指数
1
解决办法
1077
查看次数

如果没有抛出异常,则执行

如果没有抛出异常,我有一些我想要执行的代码.

目前我这样做:

try:
    return type, self.message_handlers[type](self, length - 1)
finally:
    if not any(self.exc_info()):
        self.last_recv_time = time.time()
Run Code Online (Sandbox Code Playgroud)

这可以改进吗?这是最好的方法吗?

Update0

如果控制流出try子句的末尾,则执行可选的else子句.

目前,除了异常或执行return,continue或break语句之外,控制"流出结束".

python exception finally try-catch python-3.x

5
推荐指数
2
解决办法
7127
查看次数

为什么我需要最终使用来关闭资源?

大多数时候,我唯一看到的块块就是这样的东西

FileInputStream f;
try{
    f= new FileInputStream("sample.txt");
    //something that uses f and sometimes throws an exception
}
catch(IOException ex){
    /* Handle it somehow */
}
finally{
    f.close();
}
Run Code Online (Sandbox Code Playgroud)

我的问题是,如果f的范围以封闭块结束,为什么我们需要在finally中关闭它?

java finally try-catch

5
推荐指数
2
解决办法
1856
查看次数

当try或catch块被中断时,finally块何时不执行

try或catch块被中断时finally块是什么时候不执行的?doc说"如果执行try或catch代码的线程被中断或终止,即使整个应用程序继续执行,finally块也可能无法执行".有人能举例说明这种情况吗?

java finally

5
推荐指数
2
解决办法
3万
查看次数

ThreadAbortException最终可以跳过吗?

我读过的所有内容声称线程中止将在从ThreadAbortException结束之前执行finally块.我想确认这一点,以便我可以计划如何处理可以无限期挂起的某些第三方代码.但是下面的测试让我感到困惑:

public void runTest(DateTime deadline)
{
    testThread = new Thread(() => 
    {
        try 
        {
            Console.WriteLine("test thread started at " + DateTime.Now.ToShortTimeString());
            while (true) { }
        }
        finally
        {
            Console.WriteLine("test thread entered FINALLY at " + DateTime.Now.ToShortTimeString());
            while (true) { }
        }
    });
    testThread.Start();
    while (testThread.IsAlive && deadline.Subtract(DateTime.Now).TotalSeconds > 0)
    {
        Console.WriteLine("main thread while loop " + DateTime.Now.ToShortTimeString());
        Thread.Sleep(10000);
    }
    if (testThread.IsAlive)
        testThread.Abort();
    Console.WriteLine("main thread after abort call " + DateTime.Now.ToShortTimeString());
}
Run Code Online (Sandbox Code Playgroud)

我在运行时发现的是控制台从未提到进入finally块.应用程序在.abort调用之后继续,好像根本没有finally块.难道我做错了什么?在到达最终写入控制台之前,不应该控制传递给finally块,还是执行顺序仍然是最终在单独的线程中的事实的函数?

c# multithreading finally abort

5
推荐指数
2
解决办法
4273
查看次数

C++最快的`finally`

到目前为止,C++(不幸的是)不支持finally语句的子句try.这导致了对如何释放资源的猜测.在互联网上研究了这个问题之后,虽然我找到了一些解决方案,但我并没有明白他们的表现(如果表现并不重要,我会使用Java).所以我不得不做基准测试.

选项是:

  1. CodeProjectfinally提出的基于Functor的类.它很强大,但很慢.并且反汇编表明外部函数局部变量被非常低效地捕获:逐个推送到堆栈,而不是仅仅将帧指针传递给内部(lambda)函数.

  2. RAII:堆栈上的手动清洁器对象:缺点是手动键入并为每个使用的位置定制它.另一个缺点是需要将资源释放所需的所有变量复制到其中.

  3. MSVC++特定__try/ __finally声明.缺点是它显然不便携.

我创建了这个小基准来比较这些方法的运行时性能:

#include <chrono>
#include <functional>
#include <cstdio>

class Finally1 {
  std::function<void(void)> _functor;
public:
  Finally1(const std::function<void(void)> &functor) : _functor(functor) {}
  ~Finally1() {
    _functor();
  }
};

void BenchmarkFunctor() {
  volatile int64_t var = 0;
  const int64_t nIterations = 234567890;
  auto start = std::chrono::high_resolution_clock::now();
  for (int64_t i = 0; i < nIterations; i++) {
    Finally1 doFinally([&] {
      var++;
    });
  }
  auto elapsed = std::chrono::high_resolution_clock::now() - start;
  double …
Run Code Online (Sandbox Code Playgroud)

c++ performance finally raii try-catch-finally

5
推荐指数
1
解决办法
680
查看次数

LongAdder:try 块怎么会失败?

我正在LongAdder详细分析算法。LongAdder扩展类Striped64,在该类中,基本方法是retryUpdate. 以下代码取自该方法;在链接的源代码中,它占据了第 212-222 行:

try {  // Recheck under lock
  Cell[] rs; int m, j;
  if ( (rs = cells) != null &&
       (m = rs.length) > 0  &&
       rs[j = (m - 1) & h] == null) {
     rs[j] = r;
     created = true;
   }
} finally {
  busy = 0;
}
Run Code Online (Sandbox Code Playgroud)

问题:这个try块怎么会失败?

注意数组访问

rs[j = (m - 1) & h] 
Run Code Online (Sandbox Code Playgroud)

不应该抛出 anIndexOutOfBoundsException因为按位与运算的结果总是小于或等于其整数参数的最小值,因此 0 <= j …

java algorithm finally try-catch

5
推荐指数
1
解决办法
119
查看次数

如何在 HttpClient Angular 7 中使用 finally

在以前的 Angular 版本中,我使用的finally()就像下面的代码一样

constructor(
    private http: Http
) { }

const headers = new Headers({ 'Authorization': this.authenticate.getToken(), 'Content-Type': 'application/json' });
const options = new RequestOptions({ headers: headers });

return this.http.put(Globals.SERVER_URL + '/alert/exempted?_id=' + alertId + '&isExempted=' + status + '&app_id=' + app_id, options )
                .map(this.extractData)
                .catch(this.handleError)
                .finally(() => {
                    this.exceptionSubject.next();
});
Run Code Online (Sandbox Code Playgroud)

但是现在使用 Angular 7 时,我不能再使用它了。如何在代码中插入finally(HttpClient)?这是我现有的代码:

constructor(
    private http: HttpClient
) { }

const header = new HttpHeaders({'Content-Type': 'application/json'}); 
return this.http.get(Globals.ATTENDANCE_URL + '/individual_employment_setting/detail/' + id, { headers: header }) …
Run Code Online (Sandbox Code Playgroud)

finally httpclient angular-http angular angular-httpclient

5
推荐指数
0
解决办法
1232
查看次数

Java - 检测在“finally”块期间是否有正在进行的异常

我正在从 Java 语言规范中考虑这一点:

如果 catch 块由于原因 R 突然完成,则执行 finally 块。然后有一个选择:

  • 如果 finally 块正常完成,则 try 语句由于原因 R 突然完成。

  • 如果 finally 块因原因 S 突然完成,则 try 语句因原因 S 突然完成(并且原因 R 被丢弃)。

我有一个块如下:

try {
  .. do stuff that might throw RuntimeException ...
} finally {
  try {
    .. finally block stuff that might throw RuntimeException ...
  } catch {
    // what to do here???
  }
}
Run Code Online (Sandbox Code Playgroud)

理想情况下,我希望块中的任何RuntimeException抛出finally都能逃脱,前提是它不会导致RuntimeExceptiontry块中的抛出被丢弃

Java 中有什么方法可以让我知道与块关联的finally块是否正常完成?

我猜我可以将 a …

java exception finally

5
推荐指数
1
解决办法
158
查看次数