簡體   English   中英

如何使用Scheduledexecutorservice強制創建一個線程並避免多線程

[英]How to force to create a single thread using scheduledexecutorservice and avoid multithreading

當我進入welcome.jsp頁面時,我只想執行以下JAVA代碼一次。

的welcome.jsp:

<%WeeklyScheduledMail wsm = WeeklyScheduledMail.INSTANCE;
wsm.startThread(); %>

因此,如果啟動服務器后用戶訪問該網站,則該代碼只能使用一次,而登錄並訪問welcome.jsp的其他用戶將不會執行該JAVA代碼。

首先,我嘗試使用枚舉實現Singleton模式,我認為這樣就足夠了,但是沒有用。 我也嘗試了方法的Synchronized關鍵字,但是什么也沒有...

我確定我做錯了什么,或者有更好的方法來做我想做的事情。

代碼的某些部分:

WeeklyScheduledMail.java:

public enum WeeklyScheduledMail{

    INSTANCE;

    public void startThread() {

        ScheduledExecutorService scheduler = 
        Executors.newSingleThreadScheduledExecutor();

        Runnable task = new TaskSendEmail();
        int initialDelay = 0;
        int periodicDelay = 10;
        scheduler.scheduleAtFixedRate(task, initialDelay, periodicDelay, 
        TimeUnit.SECONDS);          

    }
}

TaskSendEmail.java:

public class TaskSendEmail implements Runnable{

    public void run() {
        System.out.println("Hello: "+System.currentTimeMillis());
    }
}

您正在尋找錯誤的概念來運行應用程序初始化代碼。 JSP和向用戶公開的其他資源不是為此目的而設計的。 即使您可以強制執行一些延遲的初始化邏輯,仍然會有可避免的開銷。

JavaEE提供了您要查找的內容: 上下文偵聽器 ,該偵聽器在應用程序啟動時被調用一次,以通知您的應用程序上下文已初始化:

public class MyContextListener implements javax.servlet.ServletContextListener {

    private static fWeeklyScheduledMail wsm = 
            weeklyScheduledMail.INSTANCE;

    @Override
    public void contextInitialized(ServletContextEvent sce) {
            wsm.startThread();
    }

    @Override
    public void contextDestroyed(ServletContextEvent sce) {
        wsm.stopThread();
    }
}

然后,必須在web.xml部署描述符(在web-app )中注冊此偵聽器:

<listener>
     <listener-class>my.packg.MyContextListener</listener-class>
</listener>

當應用程序啟動時,以上代碼和配置將使您的計划運行一次。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM