Java是否具有在休眠状态下打开会话时可以使用的using语句?
在C#中,它类似于:
using (var session = new Session())
{
}
因此,对象超出范围并自动关闭。
using statement
。
using
,它会自动部署在其范围末端的对象,但它不会解除分配对象-它的生命周期还没有结束,直到它的所有引用都消失了。
Java是否具有在休眠状态下打开会话时可以使用的using语句?
在C#中,它类似于:
using (var session = new Session())
{
}
因此,对象超出范围并自动关闭。
using statement
。
using
,它会自动部署在其范围末端的对象,但它不会解除分配对象-它的生命周期还没有结束,直到它的所有引用都消失了。
Answers:
Java 7引入了自动资源块管理,该功能将该功能引入了Java平台。Java的早期版本没有任何相似之处using
。
例如,您可以使用java.lang.AutoCloseable
通过以下方式实现的任何变量:
try(ClassImplementingAutoCloseable obj = new ClassImplementingAutoCloseable())
{
...
}
java.io.Closeable
由流实现的Java 接口自动扩展AutoCloseable
,因此您可以try
像在C#using
块中使用流一样使用块中的流。这等效于C#的using
。
从5.0版开始,Hibernate Sessions实现AutoCloseable
并可以在ARM块中自动关闭。在以前的Hibernate Session中没有实现AutoCloseable
。因此,您需要使用Hibernate> = 5.0才能使用此功能。
using
做的)。
AutoCloseable
因此它们还不能使用ARM。
AutoCloseable
在Java 7之前不存在吗?
在Java 7之前,Java中没有这样的功能(对于Java 7及更高版本,请参见Asaph关于ARM 的答案)。
您需要手动进行操作,这很痛苦:
AwesomeClass hooray = null;
try {
hooray = new AwesomeClass();
// Great code
} finally {
if (hooray!=null) {
hooray.close();
}
}
这只是什么时候都// Great code
不能hooray.close()
抛出任何异常的代码。
如果您确实只想限制变量的范围,则可以使用一个简单的代码块来完成此工作:
{
AwesomeClass hooray = new AwesomeClass();
// Great code
}
但这可能不是您的意思。
// Great code
抛出异常,则Java等效项应该没有问题。
horray
可能尚未初始化(现已修复)。
从Java 7开始,它可以:http : //blogs.oracle.com/darcy/entry/project_coin_updated_arm_spec
问题中代码的语法为:
try (Session session = new Session())
{
// do stuff
}
请注意,Session
需要实现AutoClosable
或其一个(许多)子接口之一。
技术上:
DisposableObject d = null;
try {
d = new DisposableObject();
}
finally {
if (d != null) {
d.Dispose();
}
}
如果您对资源管理感兴趣,Project Lombok将提供@Cleanup
注释。直接从他们的网站上获取:
您可以
@Cleanup
用来确保在代码执行路径退出当前作用域之前自动清除给定资源。为此,您可以使用以下注释对任何局部变量声明进行@Cleanup
注释:
@Cleanup InputStream in = new FileInputStream("some/file");
结果,在您所在范围的末尾,将
in.close()
被调用。该调用保证通过try / finally构造运行。查看下面的示例以了解其工作原理。如果您要清除的对象类型没有
close()
方法,而是其他一些无参数方法,则可以像下面这样指定该方法的名称:
@Cleanup("dispose") org.eclipse.swt.widgets.CoolBar bar = new CoolBar(parent, 0);
默认情况下,清除方法假定为
close()
。带有参数的清除方法不能通过调用@Cleanup
。
香草爪哇
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();
}
}
}
与龙目岛
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);
}
}
}
在Java 8中,您可以使用try。请参考下一页。http://docs.oracle.com/javase/tutorial/essential/exceptions/tryResourceClose.html
请参阅此Java关键字列表。
using
不幸的是,该关键字不在列表中。using
Java中的其他任何关键字一样,C#关键字也没有等效性。要模仿这种"using"
行为,您将不得不使用一个try...catch...finally
块,在其中您将处置中的资源finally
。
using
是不是关键字并不意味着一件事。正如@BalusC所提到的,可以使用另一个关键字来实现(并且将实现!)相同的功能。
using
,Java关键字列表中未包含的事实意味着该功能在Java语言中不存在。那是不对的。
using
关键字,也没有任何等效项。感谢@Joachim Sauer!=)
要回答有关限制变量范围的问题,而不是谈论自动关闭/处置变量。
在Java中,您可以使用大括号定义封闭的匿名作用域。非常简单。
{
AwesomeClass hooray = new AwesomeClass()
// Great code
}
该变量hooray
仅在此范围内可用,而在该范围之外不可用。
如果您重复的变量只是临时的,这将很有用。
例如,每个带有索引。就像item
变量在for循环上关闭(即仅在其中可用)一样,index
变量在匿名作用域上关闭。
// first loop
{
Integer index = -1;
for (Object item : things) {index += 1;
// ... item, index
}
}
// second loop
{
Integer index = -1;
for (Object item : stuff) {index += 1;
// ... item, index
}
}
如果您没有for循环来提供变量作用域,但您想使用通用变量名,我有时也会使用它。
{
User user = new User();
user.setId(0);
user.setName("Andy Green");
user.setEmail("andygreen@gmail.com");
users.add(user);
}
{
User user = new User();
user.setId(1);
user.setName("Rachel Blue");
user.setEmail("rachelblue@gmail.com");
users.add(user);
}
using
做的。范围不是生命周期(using
严格来说,生命周期也不是生命周期,因为Dispose
它不会破坏对象的内存。)