用JFrame实现Java中的简单时钟
我一直在摆弄NetBeans,创建一个始终位于屏幕右下角的时钟。我已经完成了它,但我认为我的代码正在消耗内存,在我把它放了一夜之后,我又回到了1.4GB的内存和大量CPU的使用。我是Java编程新手,所以我希望这不正常 在我的主线程中,每次运行我都会创建一个新的日历对象。将其移出线程将创建一个日历对象,该对象使用当前时间初始化,但从不更新,有更好的方法吗 我不习惯与线程打交道,我想我可能已经转过身来了。有谁能建议对以下方面进行改进,以降低我的内存占用和cpu使用率用JFrame实现Java中的简单时钟,java,multithreading,swing,Java,Multithreading,Swing,我一直在摆弄NetBeans,创建一个始终位于屏幕右下角的时钟。我已经完成了它,但我认为我的代码正在消耗内存,在我把它放了一夜之后,我又回到了1.4GB的内存和大量CPU的使用。我是Java编程新手,所以我希望这不正常 在我的主线程中,每次运行我都会创建一个新的日历对象。将其移出线程将创建一个日历对象,该对象使用当前时间初始化,但从不更新,有更好的方法吗 我不习惯与线程打交道,我想我可能已经转过身来了。有谁能建议对以下方面进行改进,以降低我的内存占用和cpu使用率 public JavaCloc
public JavaClockGUI() {
initComponents();
new Thread()
{
public void run()
{
while(true)
{
Calendar cal = new GregorianCalendar();
int hour = cal.get(Calendar.HOUR_OF_DAY);
int min = cal.get(Calendar.MINUTE);
int sec = cal.get(Calendar.SECOND);
String time = String.format("%02d",hour) + ":" + String.format("%02d",min) + ":" + String.format("%02d",sec);
lblTime.setText(time);
}
}
}.start();
}
尝试在while循环之外声明变量 以及在给定的时间量上具有延迟以减少循环的执行
public void run()
{
Calendar cal;
int hour;
int min;
int sec;
String time;
while(true)
{
cal = new GregorianCalendar();
hour = cal.get(Calendar.HOUR_OF_DAY);
min = cal.get(Calendar.MINUTE);
sec = cal.get(Calendar.SECOND);
String time = String.format("%02d",hour) + ":" + String.format("%02d",min) + ":" + String.format("%02d",sec);
lblTime.setText(time);
//delay the loop for 1 sec
try {
Thread.currentThread().sleep(1000);
System.out.println(x);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
希望这对你有帮助
Date(){
DateFormat dateFormat = new SimpleDateFormat("MMM dd, yyyy HH:mm:ss)";
Date date = new Date();
boolean condition = false;
while(!false){
lbltime.setText(dateFormat.format(date));
Thread.sleep(1000);
}
}
性能有两个重要方面:
- 不要每次迭代都在循环中创建新对象(并尽可能避免堆分配)
- 定期执行任务(不要让
循环猖獗运行)while(true)
定时器
以固定速率执行定时器任务
。该方法将以相对于绝对时间的固定速率执行任务(run
method),而不是相对于上一次执行。也就是说,如果其中一个执行被延迟,那么下一个执行将开始,而不管延迟如何(它们之间的间隔将更短)。调用Thread.sleep(1000)
将不会以这种方式运行,并将导致长期累积延迟
为了接收时间并对其进行格式化,Java8日期时间API(java.time
)是一个不错的选择
public class Example {
public static void main(String[] args) {
DateTimeFormatter formatter = DateTimeFormatter.ofLocalizedTime(FormatStyle.MEDIUM);
new Timer().scheduleAtFixedRate(new TimerTask() {
@Override
public void run() {
System.out.println(LocalTime.now().format(formatter));
}
}, 0, 1000);
}
}
注释:
- 如果您不喜欢这里的匿名构造,可以让类扩展
,或者创建一个内部类TimerTaks
- 如果您不需要此格式,请浏览
,以找到所需的格式DateTimeFormatter
- 您可以保存对计时器的引用
如果你以后需要的话Timer timer = new Timer(); timer.scheduleAtFixedRate(...);
run()
方法中的while循环。这并不是真正需要的,因为秒数变化不太频繁。;-)或者你错过了发布定期调用的代码吗?@次优我认为这是我的代码的主要问题,我正在尽可能快地运行它。不幸的是,我没有遗漏这一点。谢谢你的其他建议。我现在将做一些研究。我在哪里定义线程?我当前的方法将线程定义为包装运行,因此我无法在线程内部休眠线程。我不认为……啊,是的,我认为这就是我需要的。我试过了,我已经一路降到了25mb,我想这是编译器的开销。我现在遇到的唯一问题是,我试图在静态void main中运行lblText.setText(LocalTime.now().format(formatter))
,但我得到了一个非静态变量静态上下文错误。有没有一种简单的解决方法?static
的问题是Java中与程序总体设计相关的一个基本概念。这也与这个问题无关。看吧,也许吧。您可能需要将标签设置为静态。非常感谢您让我知道。我试着投票,但我还没有代表。我也不确定是否接受这个答案,因为我仍然停留在最后一部分。谢谢你让我知道。如果你被编译器关于static
的错误所困扰,那就用一个。如果您需要关于本页中问题的澄清或帮助,请询问。