如何在Java中永远运行程序?System.in.read()是唯一的方法吗?

如何在Java中永远运行程序?System.in.read()是唯一的方法吗?,java,Java,我采取了: 第33行“System.in.read()”是否意味着它将阻塞直到有输入?当使用UNIX rc脚本启动Java应用程序时(不是从命令行手动启动),这也会起作用吗 我想编写一个Java应用程序来侦听HTTP连接。当系统引导时(使用UNIX rc脚本),应用程序将自动启动。这意味着应用程序将持续运行——理论上永远运行,直到故意停止。在Java main()方法中实现这一点的最佳方法是什么?在Java中保留main方法不会自动结束程序 如果没有更多的非守护进程线程正在运行,则JVM存在。默

我采取了:

第33行“System.in.read()”是否意味着它将阻塞直到有输入?当使用UNIX rc脚本启动Java应用程序时(不是从命令行手动启动),这也会起作用吗


我想编写一个Java应用程序来侦听HTTP连接。当系统引导时(使用UNIX rc脚本),应用程序将自动启动。这意味着应用程序将持续运行——理论上永远运行,直到故意停止。在Java main()方法中实现这一点的最佳方法是什么?

在Java中保留
main
方法不会自动结束程序

如果没有更多的非守护进程线程正在运行,则JVM存在。默认情况下,唯一的非守护进程线程是主线程,它在离开
main
方法时结束,因此停止JVM

因此,要么不要结束主线程(通过不让
main
方法返回),要么创建一个永远不会返回的新非守护进程线程(至少在希望JVM结束之前)

由于该规则实际上相当合理,因此通常有一个完美的候选线程。例如,对于HTTP服务器,它可能是实际接受连接并将其交给其他线程进行进一步处理的线程。只要代码还在运行,JVM就会继续运行,即使
main
方法已经运行了很长时间。

while(true){…}
应该持续很长时间。当然,你最终得想办法阻止它


一个常见的技巧是让一些
volatile boolean running=true
,然后让主循环在(running){…}时成为
,并定义一些条件,线程根据这些条件设置
running=false

@Joachim的答案是正确的

但是,如果(出于某种原因)仍然希望无限期地阻止主方法(不进行轮询),则可以执行以下操作:

public static void main(String[] args) {
    // Set up ...
    try {
        Object lock = new Object();
        synchronized (lock) {
            while (true) {
                lock.wait();
            }
        }
    } catch (InterruptedException ex) {
    }
    // Do something after we were interrupted ...
}

由于lock对象仅对此方法可见,因此没有任何东西可以通知它,因此
wait()
调用不会返回。但是,其他一些线程仍然可以取消阻止
main
线程。。。通过打断它。

这看起来像是一个奇怪的黑魔法,但下面的动作非常优雅

Thread.currentThread().join();
因此,当前线程,例如
main
,等待线程
main
join()
结束。陷入僵局


被阻止的线程当然不能是守护进程线程。

回到线程,这正是我想要的。顺便说一句,这对我帮助很大

Main.java

public class Main {
    public static void main(String args[]) {
        ChatServer server = null;
        /*if (args.length != 1)
            System.out.println("Usage: java ChatServer port");
        else*/
            server = new ChatServer(Integer.parseInt("8084"));
    }
}
java类扩展了一个可运行的

public class ChatServer implements Runnable
{  private ChatServerThread clients[] = new ChatServerThread[50];
    private ServerSocket server = null;
    private Thread       thread = null;
    private int clientCount = 0;

    public ChatServer(int port)
    {  try
    {  System.out.println("Binding to port " + port + ", please wait  ...");
        server = new ServerSocket(port);
        System.out.println("Server started: " + server);
        start(); }
    catch(IOException ioe)
    {
        System.out.println("Can not bind to port " + port + ": " + ioe.getMessage()); }
    }

    public void start() {  
        if (thread == null) {  
            thread = new Thread(this);
            thread.start();
        }
    }
.... pleas continue with the tutorial
因此,在main方法中,将实例化一个Runnable,并创建一个新线程,如
public void start(){
正在使用runnable进行实例化。 这种情况下,JVM将继续执行该进程,直到您退出项目或调试器


顺便说一句,这与Joachim Sauer在其Answare中发布的内容相同。

此外,我们还可以通过ReentrantLock和调用wait()来实现这一点:


不要停止
httpService
?我考虑使用“while(true);”循环,但运行此函数的线程是否会持续计算表达式,从而消耗不必要的CPU周期?这取决于它在做什么。如果它将大部分时间用于等待来自HTTP连接的数据,那么它就不会消耗不必要的CPU周期。我应该澄清一下,我不是建议使用空的循环(称为忙等待),而是一个主事件循环。理论上,
wait
可能会错误地唤醒(没有相应的
notify()
调用)。这就是为什么你不应该在循环外调用它。你没有完全回答这个问题。你没有说如何阻止非守护进程线程。正如我在下面发布的那样,非常优雅的方法是调用
thread.currentThread().join();
。在主线程上故意阻塞而没有任何实际工作要做是错误的方法。最好将实际工作的线程标记为非守护线程。如果没有这样的线程,那么问题是为什么需要运行JVM;-)这工作得很好。不确定是否还有其他问题
public class ChatServer implements Runnable
{  private ChatServerThread clients[] = new ChatServerThread[50];
    private ServerSocket server = null;
    private Thread       thread = null;
    private int clientCount = 0;

    public ChatServer(int port)
    {  try
    {  System.out.println("Binding to port " + port + ", please wait  ...");
        server = new ServerSocket(port);
        System.out.println("Server started: " + server);
        start(); }
    catch(IOException ioe)
    {
        System.out.println("Can not bind to port " + port + ": " + ioe.getMessage()); }
    }

    public void start() {  
        if (thread == null) {  
            thread = new Thread(this);
            thread.start();
        }
    }
.... pleas continue with the tutorial
public class Test{
private static Lock mainThreadLock = new ReentrantLock();

public static void main(String[] args) throws InterruptedException {

System.out.println("Stop me if you can");
synchronized (mainThreadLock) {
    mainThreadLock.wait();
 }
}