Runtime.getRuntime().addShutdownHook()

解决方案 »

  1.   

    你可以响应相关的事件来处理,finalize()必须要垃圾收集的时候才会被执行,问题多多,你怎知什么时候收集,System.gc()不好吧。
      

  2.   

    哇!masterz又说话了!!!!!!!
    gz
    gz
    gz
    gz
      

  3.   

    Runtime.getRuntime().addShutdownHook()想要执行的代码写在哪里?
      

  4.   

    Runtime.getRuntime().addShutdownHook();Error #: 300 : method addShutdownHook(phpc.PhPCServer) not found in class java.lang.Runtime at line 23, column 26这是怎么回事儿?完全搞糊涂了。唉!java的doc也不给几个例子。
      

  5.   

    http://www.smotricz.com/kabutz/Issue011.html
    2001-02-28 TJSN [Issue 011] - Hooking into the shutdown call
    Author: Dr. Heinz M. Kabutz
    If you are not already subscribed to this newsletter, please send an email to [email protected]. Be warned that if you are a beginner in Java, you will at times struggle to keep up. The archive of past newsletters is kept at http://www.javaspecialists.co.za 
    --------------------------------------------------------------------------------Welcome to the 11th issue of "The Java(tm) Specialists' Newsletter", where we have a "gloves-off" approach to the Java(tm) language and development environment. Thank you again for your support and the feedback you send me. I am sitting outside in a mild South African summer evening, looking up at the Southern Cross hoping the milky way will inspire me to bring you a newsletter that is worth not pressing delete on. I am always interested in hearing about "gotchas" that you found while using Java, so please keep on sending me your ideas. Since the GUI is 63% of the JDK, I was tempted to send another interesting bit about setting the focus to a component besides the first one on a modal dialog. This seemingly simple problem had me quite stumped, but luckily the Cape Town Java User Group gave me one solution and I found another solution myself. Next week I will write about that, so stay tuned. I know that "real" programmers don't write GUIs, but if you are a "real" Java programmer, other less real programmers might ask you how to do these fancy tricks, and it's good to then have an answer ;-) There is another newsletter in the pipeline that tells you how to serialize GUI components across the network. Hooking into the shutdown call
    Last year, while I was trying out the jBoss EJB application server, I happened to notice that you could shutdown the server by pressing CTRL+C. Somehow, the server "knew" you had killed the program, and shutdown all the necessary services before exiting the Java VM. My Java-Guru-In-The-Making colleague told me that it was possible to add a "shutdown hook" which would be called when the application was being shutdown. This shutdown event would happen when you call System.exit(), which in turn gets called when you press CTRL+C. As was hinted in last week's newsletter, once you use any GUI components, the VM starts up GUI threads that you cannot shutdown cleanly. This means that the only option you have of exiting your program is to call System.exit()!!! However, System.exit() can be called from anywhere in your program and if it gets called, we want to have a central place where we can add methods that will be called when we want to exit. This central place was added, without much fanfare (actually no fanfare at all!), in JDK 1.3, together with many other cool features like the java.awt.Robot. Here is an example of how you could add a shutdown hook into the current VM runtime. You do this by constructing a new Thread and passing that to the runtime to start when it wants to shutdown.   public class ShoutdownTrick {
        public static void main(String args[]) {
          Runtime.getRuntime().addShutdownHook(new Thread() {
            public void run() {
              System.out.println("You wanna quit, hey?");
              System.out.println("... fry eggs on your CPU.");
              while(true);
            }
          };
          System.out.println("Let's take a break...");
          try {
            Thread.sleep(5000);
          }
          catch(InterruptedException ex) {}
          System.out.println("That's it, I'm outta here");
          System.exit(0);
          System.out.println("This line will not show!");
        }
      }Try run this on your machine and you will notice that the only way to stop the program is via the task manager. This of course highlights one of the problems with writing code to call during shutdown. What happens when the shutdown code does not exit? I am told that in Delphi you can solve the Halting Problem, unfortunately Java is not that powerful, so the VM cannot know whether the shutdown code will stop or not. Ideally, you should in the shutdown code only do what is absolutely necessary to put the system in a state that is usable next time you want to run the program, i.e. close DB connections cleanly, close log files, etc. A feature I did not know about until tonight is that you can bypass the shutdown hooks and actually "halt" the VM without further ado. So, the obvious next step in our Shutdown Hook example is to add another thread that will halt the VM after some timeout:   public class ShoutdownTrickWithHaltTimeout {
        public static void main(String args[]) {
          Runtime.getRuntime().addShutdownHook(new Thread() {
            public void run() {
              System.out.println("You wanna quit, hey?");
              System.out.println("... fry eggs on your CPU.");
              while(true);
            }
          });
          Runtime.getRuntime().addShutdownHook(new Thread() {
            public void run() {
              try {
                Thread.sleep(10000);
              } catch(InterruptedException ex) {}
              // halt will bail out without calling further shutdown hooks or
              // finalizers
              Runtime.getRuntime().halt(1);
            }
          });
          System.out.println("Let's take a break...");
          try {
            Thread.sleep(5000);
          }
          catch(InterruptedException ex) {}
          System.out.println("That's it, I'm outta here");
          System.exit(0);
          System.out.println("This line will not show!");
        }
      }The problem with this code is that even though you know that after 10 seconds you will definitely halt the VM, you will have to wait for 10 seconds each time you try to exit the VM, because there is no way of knowing if the other threads are finished yet. This brings out another interesting feature, which is that all the shutdown hooks are threads and it seems that they are all started at the same time. The obvious solution is to make the "Halting" shutdown thread a Daemon thread, but, alas, at that point in the VM processing, it doesn't matter whether a thread is a Daemon thread or not, it will run until it is finished. It seems that, even though our friends at Sun have noticed that such a shutdown hook feature is necessary, they have not fully thought through the possibilities of what could go wrong and how to solve it. Perhaps a System.exit(int status, long timeout) would be appropriate? There are some really cool extras in JDK 1.3 which are not very widely publicised, or perhaps I'm reading the wrong magazines? Shall we take a bet how long it takes before all the System.exit(0) code in the world is replaced with Runtime.getRuntime().halt(0)? Until next week Heinz 
      

  6.   

    masterz,非常感谢你提供的资料,非常有效。
    不过我的情况有些特殊,作为一个服务器程序,程序经常是在ServerSocket.accept()函数调用的时候被中断。用你上面的方法就不好用了。不知道还有没有其他方法?或者是否可能用上面方法稍作改进处理这个问题?
      

  7.   

    you can use socketchannel
      

  8.   

    2003年2月份的程序员java专家门诊有详细地说明!!代码如下:package test.hook;import java.io.*;public class Main
    {
    public static void main(String args) throws Exception
    {
    Runtime.getRuntime().addShutdownHook(new Hooker(1));
    System.out.println("Server running...");
    System.out.println("Press CTRL+C to exit.");

    while(true)
    {
    Thread.sleep(1000);
    System.out.println(In loop.);

    }
    }
    }class Hooker extends Thread
    {
    private int code;
    public Hooker()
    {
    this.code=code;
    }

    public void run(){
    System.out.println(code+"Begin to terminal process.");

    try{
    Thread.sleep(2000);
    }catch(Exception e){}
    }
    }