Java tutorial表示您可以使用try-with-resources
执行以下操作:
try (Statement stmt = con.createStatement()) {
ResultSet rs = stmt.executeQuery(query);
...
} catch (SQLException e) {
...
}
在本教程中,ResultSet
永远不会关闭,因此我想要包含ResultSet
,因为它还实现了AutoCloseable
接口,如下所示:
try (Statement stmt = con.createStatement();
ResultSet rs = stmt.executeQuery(query)) {
...
} catch (SQLException e) {
...
}
这很好用,但是当谈到PreparedStatements
时,我希望能够在执行查询之前在上设置一些值:
String name = "Ian";
try (PreparedStatement pstmt = getPreparedStatement(con, stmt);
pstmt.setString(1, name);
ResultSet rs = pstmt.executeQuery(query)) {
...
} catch (SQLException e) {
...
}
这会导致一系列编译错误,因为(我假设)只允许变量赋值。
无论如何在同一try-with-resources
区块中整齐地做这件事吗?
我已经想到了:
考虑以下情况:
try (MyObject1 o1 = new MyObject1()) {
o1.setSomeValue();
try (MyObject2 o2 = new MyObject2(o1)) {
o2.setSomeValue();
try (MyObject3 o3 = new MyObeject3(o2) {
o3.setSomeValue();
// do work here
}
}
} catch (Exception e) {
...
}
VS
try (MyObject1 o1 = new MyObject1();
o1.setSomeValue();
MyObject3 o2 = new MyObeject2(o1);
o2.setSomeValue();
MyObject3 o3 = new MyObeject3(o2);
o3.setSomeValue()) {
// do work here
} catch (Exception e) {
...
}
setString()
方法返回对象并将其包含在赋值类似的东西:
public PreparedStatement createPreparedStatement(Connection con, String stmt, Object ... params) {
}
答案 0 :(得分:3)
我猜你的意思是Connection.prepareStatement()
。
由于Statement.close
的API-Doc保证关闭其ResultSet,因此无需明确关闭ResultSet。所以写的很好
try (PreparedStatement stmt = con.prepareStatement(query)) {
stmt.setString(1, name);
ResultSet rs = stmt.executeQuery(query);
...
}
catch (SQLException e) {
...
}
答案 1 :(得分:1)
如果要在构造Statement
和ResultSet
之间设置一些值,则需要嵌套的try-with-resources块。你为什么试图避免这种情况?这样做没有错。
你可以定义一些笨拙的辅助方法,但除了一些非常高用量的情况之外,这将比它的价值更麻烦。
答案 2 :(得分:0)
你可以喜欢这个:
try (
Connection con = em.unwrap(Connection.class);
PreparedStatement ps = TryJumper.jump(con.prepareStatement("select * from x where a = ?"), pss -> {
pss.setInt(1, 123);
});
ResultSet rs = ps.getResultSet();
) {
//core codes
} catch (Exception e) {
e.printStackTrace();
}
必修课
public class TryJumper {
public static <M> M jump(M m, MUser<M> mUser) throws Exception {
mUser.consume(m);
return m;
}
interface MUser<M> extends AutoCloseable {
void consume(M m) throws Exception;
@Override
default void close() throws Exception {
}
}
}
它是如何工作的:
在 try catch 资源中,一切都应该返回一个从 Object
接口实现的 AutoClosable
。此类仅返回您在使用方法工作后传递的相同对象(在 lambda
中)