【问题标题】:Use JAVA timer in the background without causing any lag in the UI在后台使用 JAVA 计时器,不会在 UI 中造成任何延迟
【发布时间】:2018-08-01 16:33:30
【问题描述】:

我正在制作一个自动将数据发送到我的远程服务器的 java 应用程序。 我需要的是插入数据而不会让最终用户感到滞后。远程数据库更新部分应该在后台运行。我尝试了swingworker,线程但没有任何效果。仍然落后于我的应用程序。这是我到目前为止所做的事情

public class uploader extends Thread {

    static Socket socket;
    static Timer ttt;

    public void run() {
        try {
            ttt = new Timer(15000, new ActionListener() {
                @Override
                public void actionPerformed(ActionEvent e) {

                    try {

                        socket = new Socket("192.168.10.1", 3306);                   

//upload
                        ResultSet rs = DB.search("select query,id FROM general_log where state = 0 order by id asc");
                        while (rs.next()) {
                            try {
                                socket = new Socket("192.168.10.1", 3306);
                                DB2.acknowledge(rs.getString(1));
                                DB.acknowledge("update general_log set state = 1 where id = '" + rs.getString(2) + "'");

                            } catch (Exception e1) {
                                e1.printStackTrace();
                                System.out.println("error");
                                break;
                            }

                        }

                    } catch (Exception e3) {
                        System.out.println("error");
                        e3.printStackTrace();
                    }

                }
            });
            ttt.start();


        } catch (Exception e) {
            e.printStackTrace();

        }

    }

}

我在启动时运行它

Thread upl = new Thread(new uploader());
upl.start();

每 15 秒本地数据应上传到远程服务器。但是在这里,当计时器运行时,我的 UI 会滞后 15 秒。

我怎样才能做到不造成延迟? 提前致谢。

【问题讨论】:

  • Swing Timer 中的代码在 Event Dispatch Thread (EDT) 上执行,这会阻止 GUI 在任务完成之前自行更新。您应该创建一个单独的线程来执行长时间运行的任务。所以基本上你的代码是相反的。当您的应用程序启动时,您不应该启动线程。相反,您启动计时器。然后 Timer 将启动 Thread 进行服务器更新。
  • 嗨。谢谢。但它不是每 15 秒创建一次新线程吗?
  • 您到底为什么要为ResultSet 的每一行创建一个新的Socket

标签: java multithreading swing concurrency timer


【解决方案1】:

您可以使用索引优化您的 SQL 查询,这是肯定的。

除了主要问题之外,使用在new Handler() 启动的定时器任务不是更好吗?

============================================

例如,而不是类创建一个方法:

private final Handler handler = new Handler();
private TimerTask timerTask;
private Timer timer = new Timer();



...

    public void sendBackgroundData() {

    timerTask = new TimerTask() {
        @Override
        public void run() {
            handler.post(() -> {

DO YOUR CODE

                    }
            });
        }
    };
    timer.schedule(timerTask, 0, 2000);
}

【讨论】:

  • 很抱歉我是新手。我该如何实现?
  • @UthpalaBandara,TimerTask 与 Timer 相同,只是它在不同的线程中运行。阅读 TimerTask 的 API。您还可以在论坛/网络上搜索使用该类的示例。
  • @Jawegiel 你也可以添加导入吗?谢谢。
  • 过失,我很困惑它是 Android 的方式来创建异步任务调用一段代码每 X 秒。在普通的 Java 中应该是类似的。对不起,伙计!
  • 在纯 Java 中,它是 java.util.TimerTask,但不建议使用那个旧类。相反,最好的解决方案是java.util.concurrent.ScheduledExecutorService,最好通过java.util.concurrent.Executors.newScheduledThreadPool(1) 获得(一个是线程数)。然后,使用scheduleAtFixedRatescheduleWithFixedDelay
猜你喜欢
  • 2019-11-06
  • 1970-01-01
  • 1970-01-01
  • 2018-04-23
  • 1970-01-01
  • 1970-01-01
  • 2016-09-19
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多