Это должно хорошо использовать выгоду попытки внутри наконец?

Я использую буферизированное устройство записи и мой код, окружает устройство записи наконец блок. Мой код похож на это.

 ...........
    BufferedWriter theBufferedWriter = null;
    try{
    theBufferedWriter =.....
    ....
    ......
    .....
    } catch (IOException anException) {
    ....
    } finally {
        try {
            theBufferedWriter.close();              
        } catch (IOException anException) {
            anException.printStackTrace();
            }
    }

Я должен использовать выгоду попытки в коде уборки в наконец, поскольку theBufferedWriter мог бы также бросить IOException. Я не хочу выдавать это исключение к вызову methos. Действительно ли это - хорошая практика для использования выгоды попытки в наконец? Если не, какова альтернатива? Предложите.

С уважением, Hiral

22
задан Hiral Lakdavala 16 June 2010 в 07:07
поделиться

6 ответов

Более удобный способ сделать это - использовать IOUtils.closeQuiety из Apache commons-io . Он сохраняет ваш код в чистоте и устраняет часть шаблонов, присущих Java.

Ваш код становится:

BufferedWriter theBufferedWriter = null;
try{
    theBufferedWriter = ...
    ...
} catch (IOException anException) {
    ...
} finally {
    IOUtils.closeQuietly(theBufferedWriter);
}

Намного красивее и выразительнее.

14
ответ дан 29 November 2019 в 05:15
поделиться

Все в порядке, но перед закрытием следует проверить, не является ли theBufferedWriter нулевым.
Вы также можете:

BufferedWriter theBufferedWriter;
try {
    theBufferedWriter = new ...
    try {
        ...
    } finally {
        try {
            theBufferedWriter.close();
        } catch (IOException closeException) {
            closeException.printStackTrace();
        }
    }
} catch (IOException anException) {
    ...
}

или:

BufferedWriter theBufferedWriter;
try {
    theBufferedWriter = new ...
} catch (IOException createException) {
    // do something with createException 
    return;  // assuming we are in a method returning void
}

try {
    ...
} catch (IOException anException) {
    ...
    // assuming we don't return here
}

try {
    theBufferedWriter.close();
} catch (IOException closeException) {
    closeException.printStackTrace();
}

, но в основном я выполняю такие операции (например, запись файла) в специальном методе и предпочитаю генерировать исключение / an Exception, чтобы вызывающий мог его обработать (например, запрашивая другой файл, остановка приложения, ...):

void someMethod(...) throws IOException {
    BufferedWriter theBufferedWriter = new ...

    try {
        ...
    } catch (IOExcepption anException) {
        try {
            theBufferedWriter.close();
        } catch (IOException closeException) {
            closeException.printStackTrace();
            // closeException is not thrown, anException represents the main/first problem
        }
        throw anException;
    }

    theBufferedWriter.close();  //  throws the Exception, if any
}

Обратите внимание: английский не является моим первым и не вторым языком, любая помощь приветствуется

1
ответ дан 29 November 2019 в 05:15
поделиться

Или вы можете использовать Lombok и аннотацию @Cleanup , и вам больше никогда не придется снова писать пробную ловушку внутри.

Обычно это делается так (обратите внимание, что вызывает исключение IOException ):

//Vanilly Java

import java.io.*;

public class CleanupExample {
  public static void main(String[] args) throws IOException {
    InputStream in = new FileInputStream(args[0]);
    try {
      OutputStream out = new FileOutputStream(args[1]);
      try {
        byte[] b = new byte[10000];
        while (true) {
          int r = in.read(b);
          if (r == -1) break;
          out.write(b, 0, r);
        }
      } finally {
        out.close();
      }
    } finally {
      in.close();
    }
  }
}

Теперь с Lombok вы просто пишете @Cleanup в потоках

import lombok.Cleanup;
import java.io.*;

 public class CleanupExample {
   public static void main(String[] args) throws IOException {
     @Cleanup InputStream in = new FileInputStream(args[0]);
     @Cleanup OutputStream out = new FileOutputStream(args[1]);
     byte[] b = new byte[10000];
     while (true) {
       int r = in.read(b);
       if (r == -1) break;
       out.write(b, 0, r);
     }
   }
 }
3
ответ дан 29 November 2019 в 05:15
поделиться

Это то, с чем нам придется жить до Java 7 и Блоки ARM .

1
ответ дан 29 November 2019 в 05:15
поделиться

В версии до Java 7 я бы сказал, что то, что вы написали, является лучшим решением.

В Java 7 и далее у вас есть Автоматическое управление ресурсами, призванное упростить эти вещи. С помощью этой функции вы можете сделать

BufferedWriter theBufferedWriter = null;
try (BufferedWriter theBufferedWriter = ...) {
....
......
.....
} catch (IOException anException) {
....
}
12
ответ дан 29 November 2019 в 05:15
поделиться

Можно добавить try-catch в файл finally. Это инструмент, который делает то, что вы хотите. Однако я чувствую, что выброшенное IOException при закрытии достаточно необычно, чтобы я позволил ему подавить любое исключение в теле таким образом.

try {
    BufferedWriter writer = .....
    try {
        .....
    } finally {
       writer.close();
    }
 } catch (IOException e) {
     ....
 }
0
ответ дан 29 November 2019 в 05:15
поделиться
Другие вопросы по тегам:

Похожие вопросы: