Kli*_*cou 7 java shutdown-hook java-io
我有一些临时文件,我打电话deleteOnExit()给.我也有一个可以运行的runnable,addShutdownHook()可以在System.exit调用时运行.
我的关机挂钩运行时是否保证临时文件仍然可用?
Ana*_*san -1
当我们查看下面的实现时,两者都在处理 Shutdown-Hook。
当我们处理addShutdownHook(ApplicationShutdownHooks)时,我们的代码中有如下一段代码。
Runtime.getRuntime().addShutdownHook(new Thread() {
public void run() {
<<---Do the Implementations here--->>
}
});
Run Code Online (Sandbox Code Playgroud)在 Java 源代码内部,ApplicationShutdownHooks 的实现如下,并从 Runtime 类调用,如链接http://www.docjar.com/html/api/java/lang/Runtime.java.html中所述
class ApplicationShutdownHooks {
/* The set of registered hooks */
private static IdentityHashMap<Thread, Thread> hooks;
static {
try {
Shutdown.add(1 /* shutdown hook invocation order */,
false /* not registered if shutdown in progress */,
new Runnable() {
public void run() {
runHooks();
}
}
);
Run Code Online (Sandbox Code Playgroud)
而当我们处理 File.deleteOnExit() 时,Java 会在内部注册关闭,如下所示。
// DeleteOnExitHook must be the last shutdown hook to be invoked.
// Application shutdown hooks may add the first file to the
// delete on exit list and cause the DeleteOnExitHook to be
// registered during shutdown in progress. So set the
// registerShutdownInProgress parameter to true.
sun.misc.SharedSecrets.getJavaLangAccess()
.registerShutdownHook(2 /* Shutdown hook invocation order */,
true /* register even if shutdown in progress */,
new Runnable() {
public void run() {
runHooks();
}
}
);
Run Code Online (Sandbox Code Playgroud)
注意:上面注册钩子的代码可以在JavaSourceCode中找到,如下所示:http://hg.openjdk.java.net/icedtea/jdk7/jdk/file/10672183380a/src/share/classes/java/io/ DeleteOnExitHook.java http://hg.openjdk.java.net/icedtea/jdk7/jdk/file/10672183380a/src/share/classes/java/io/File.java
如果关机挂钩运行正常,我们将从系统中清除所有文件。但是,不能保证 Shutdown Hooks 每次都能正常运行。还有一些罕见的场景,您可以参考以下链接:
ApplicationShutdownHooks:https://docs.oracle.com/javase/7/docs/api/java/lang/Runtime.html#addShutdownHook (java.lang.Thread)
deleteOnExit: https://docs.oracle.com/javase/7/docs/api/java/io/File.html#deleteOnExit()
更具体地说,我们应该使用ApplicationShutdownHooks 而不是deleteOnExit(),因为deleteOnExit() 使用大量内存,这些内存在JVM 终止之前不会被释放。
注意:由于deleteOnExit()适用于File实例而不是Path,我们还需要通过调用以下方法将Path转换为文件:
Path path = FileSystems.getDefault.getPath(".");
File asFile = path.toFile();
asFile.deleteOnExit();
Run Code Online (Sandbox Code Playgroud)