将方法参数的所有权传递给“尝试使用资源”块

时间:2016-06-30 18:40:44

标签: java try-with-resources

我对Java的“尝试资源”功能有疑问。大多数示例似乎遵循在try语句中声明和实例化资源的模型,如下所示:

try (BufferedReader in =
        new BufferedReader(new InputStreamReader(socket.getInputStream())); ) {
  ...
}

我需要将一个可关闭的资源传递给一个方法,我想知道将一个方法参数作为方法参数传递的可关闭资源的所有权传递给try块是否可行或可取。例如:

void handleConnection(Socket clientSocket) {
    try (Socket socket = clientSocket;
         BufferedReader in =
             new BufferedReader(new InputStreamReader(socket.getInputStream())); ) {
        ...
    }

这会正确清理clientSocket实例吗?我希望避免在我的代码中显式关闭clientSocket实例。

1 个答案:

答案 0 :(得分:2)

虽然这在技术上是正确的,但它很危险。许多AutoCloseable(包括Socket)在关闭后无法重新开启。因此,handleConnection方法的用户必须知道传递给您的方法的对象不能再使用。让对象的所有者处理它的生命周期可能是个更好的主意。您可以通过创建一个包装类来实现这一点,该包本身实现了AutoCloseable,如下所示。

public class SocketHandler implements AutoCloseable {
    private final Socket clientSocket;

    public SocketHandler(Socket clientSocket) {
        if (clientSocket == null) {
            throw new IllegalArgumentException("Socket cannot be null");
        }
        this.clientSocket = clientSocket;
    }

    public void handle() {

    }

    @Override
    public void close() throws Exception {
        clientSocket.close();
    }

}