java中的定時器和多線程
定時器和多線程
1、任務(wù)簡介
本文分享的是杜老師《工程訓(xùn)練》任務(wù)2.3中的普通任務(wù),通過該任務(wù)我們可以初步學(xué)習(xí)Java中定時器與多線程的相關(guān)知識,該任務(wù)我是在5月完成的,但是一直未將該部分任務(wù)上傳,故今天對該部分任務(wù)的學(xué)習(xí)進(jìn)行敘述,詳細(xì)的思路和代碼在下文中進(jìn)行分享。
2、基本任務(wù)和代碼
(1)任務(wù)1
- 1)任務(wù)內(nèi)容
完成一個java application應(yīng)用程序,使用定時器編程,在實時顯示當(dāng)前時間,每1秒時鐘內(nèi)容更新一次。
- 2)任務(wù)代碼
我首先需要了解java定時器的作用,在應(yīng)用開發(fā)中,經(jīng)常需要一些周期性的操作,比如每5分鐘執(zhí)行某一操作等,對于這樣的操作最方便、高效的實現(xiàn)方式就是使用java.util.Timer工具類,即使用java定時器,其中Timer有兩個核心的屬性,一個是TaskQueue對象,用于存儲任務(wù)隊列,一個是TimerThread,用于執(zhí)行隊列中的任務(wù);
要運行一個定時任務(wù),最基本的步驟如下:首先建立一個要執(zhí)行的任務(wù)TimerTask,然后創(chuàng)建一個Timer實例,通過Timer提供的schedule()方法,將 TimerTask加入到定時器Timer中,同時設(shè)置執(zhí)行的規(guī)則即可,當(dāng)程序執(zhí)行了Timer初始化代碼后,Timer定時任務(wù)就會按照設(shè)置去執(zhí)行;
對于Timer中的schedule()方法及其語句的詳解
如下圖所示:
對于系統(tǒng)當(dāng)前時間的定義方法在任務(wù)1.3中已經(jīng)學(xué)習(xí)過了,可以借鑒任務(wù)1.3的格式來定義當(dāng)前的系統(tǒng)時間,在對Timer方法進(jìn)行了簡單的學(xué)習(xí)之后,我準(zhǔn)備使用Myeclipse編寫程序來實現(xiàn)任務(wù)所要求的功能
代碼如下:
//每1S刷新顯示當(dāng)前系統(tǒng)時間 import java.text.SimpleDateFormat;//導(dǎo)入java.text包下的SimpleDateFormat類 import java.util.Date; import java.util.Timer; import java.util.TimerTask; //import java.util.*;//導(dǎo)入java.util包下的所有類 public class Timer1 {//類名 public static void main(String[] args){//程序主函數(shù) Timer time=new Timer();//創(chuàng)建一個Timer類的實例 MyTask task=new MyTask();//創(chuàng)建一個MyTask類的實例 time.schedule(task, 0,1000);//指定無延遲的運行,并且刷新時間為1S } } class MyTask extends TimerTask{//創(chuàng)建一個MyTask類繼承于父類TimerTask public void run(){//run方法,里面包含需要執(zhí)行的任務(wù) SimpleDateFormat simpleDateFormat=null;//初始化當(dāng)前時間 //獲取當(dāng)前時間信息,并定義其格式 SimpleDateFormat t=new SimpleDateFormat("yyyy-MM-dd"+" "+"HH:mm:ss"); String a=t.format(new Date());//將當(dāng)前時間信息賦給變量a System.out.println("當(dāng)前系統(tǒng)時間為:"+a);//輸出當(dāng)前時間信息 } }
- 3)運行結(jié)果
(2)任務(wù)2
- 1)任務(wù)內(nèi)容
完成一個java application應(yīng)用程序,在應(yīng)用程序主進(jìn)程中新開一個線程,此線程進(jìn)行死循環(huán),每1秒被激活一次,激活時即在輸出顯示當(dāng)前時間。
- 2)任務(wù)代碼:
在對定時器的知識進(jìn)行學(xué)習(xí)之后,我們需要學(xué)習(xí)java中多線程的知識,Java 給多線程編程提供了內(nèi)置的支持,一條線程指進(jìn)程中一個單一順序的控制流,一個進(jìn)程中可以并發(fā)多個線程,每條線程并行執(zhí)行不同的任務(wù),用多線程只有一個目的,那就是更好的利用CPU的資源,而每一個線程都有自己的生命周期,如下圖所示:
Java 提供了三種創(chuàng)建線程的方法:
1、通過實現(xiàn) Runnable 接口;
2、通過繼承 Thread 類本身;
3、通過 Callable 和 Future 創(chuàng)建線程;我本次編寫程序選擇使用繼承Thread 類創(chuàng)建線程,每隔1S激活一次,并顯示當(dāng)前的系統(tǒng)時間,程序代碼如下:
import java.text.SimpleDateFormat;//導(dǎo)入java.text包下的SimpleDateFormat類 import java.util.Date;//導(dǎo)入java.util包下的Date類 public class Timer2 {//類名 public static void main(String[] args) {//程序主函數(shù) Thread t=new Thread();//創(chuàng)建一個新的線程 date d=new date();//創(chuàng)建一個date類對象 d.start();//開啟線程 } } class date extends Thread{//創(chuàng)建一個date類繼承于父類Thread public void run(){//run方法,里面包含需要執(zhí)行的任務(wù) while (true){//定義死循環(huán) try{//try代碼塊,當(dāng)發(fā)生異常時會轉(zhuǎn)到catch代碼塊中 Thread.sleep(1000);//死循環(huán)中的線程每隔一秒激活一次 SimpleDateFormat simpleDateFormat=null;//初始化當(dāng)前時間 //獲取當(dāng)前時間信息,并定義其格式 SimpleDateFormat d=new SimpleDateFormat("yyyy-MM-dd"+" "+"HH:mm:ss"); String a=d.format(new Date());//將當(dāng)前時間信息賦給變量a System.out.println("當(dāng)前系統(tǒng)時間為:"+a);//輸出當(dāng)前時間信息 } catch(InterruptedException e){//當(dāng)try代碼塊有異常時轉(zhuǎn)到catch代碼塊 } } } }
- 3)運行結(jié)果
(3)任務(wù)3
- 1)任務(wù)內(nèi)容
完成一個java application應(yīng)用程序,此應(yīng)用程序公共類有一個double型類屬性(變量)x,初始值為0;在應(yīng)用程序主進(jìn)程中新開兩個線程,這兩個線程都進(jìn)行死循環(huán);第1個線程每隔300ms激活一次,令類屬性x自加1.0并輸出顯示;第2個線程每隔400ms激活一次,令類屬性x自加0.1并輸出顯示。
- 2)任務(wù)代碼
前一個步驟中只使用了一個線程來執(zhí)行任務(wù),而在本步驟中需要創(chuàng)建兩個線程來同時執(zhí)行任務(wù),故真正需要使用到多線程的知識,分別對兩個線程進(jìn)行定時,并在每次激活后對x進(jìn)行輸出,并且在指定時間間隔后輸出一次x的值;
對于該程序中的兩個線程我需要分別通過Runnable接口來創(chuàng)建,并使它們在規(guī)定的激活間隔后輪流對x進(jìn)行加法操作,并在每次操作后都要輸出x的值,其中需要使用語句Thread a=new Thread(new AThread());來分別創(chuàng)建新的線程類,程序代碼如下所示:
public class Timer3{//類名 static double x=0; //定義一個浮點型變量并賦值 public static void main(String[] args){//程序主函數(shù) Thread a=new Thread(new AThread());//建立一個新的線程的對象,這里只能引用靜態(tài)的方法 Thread b=new Thread(new BThread());//建立一個新的線程的對象,這里只能引用靜態(tài)的方法 System.out.println("初值:"+x);//輸出浮點型變量x的初值 a.start();//開啟線程a b.start();//開啟線程b } public static class AThread implements Runnable{//通過實現(xiàn)Runnable接口來創(chuàng)建線程類 public void run(){//run方法,里面包含需要執(zhí)行的任務(wù) try{//try代碼塊,當(dāng)發(fā)生異常時會轉(zhuǎn)到catch代碼塊中 while(true){//定義死循環(huán) Thread.sleep(300);//死循環(huán)中的線程每300ms激活一次 x+=1;//x=x+1 System.out.println("線程1:"+x);//在控制臺輸出x } } catch(InterruptedException e){}//當(dāng)try代碼塊有異常時轉(zhuǎn)到catch代碼塊 } } public static class BThread implements Runnable{//通過實現(xiàn)Runnable接口來創(chuàng)建線程類 public void run(){//run方法,里面包含需要執(zhí)行的任務(wù) try{//try代碼塊,當(dāng)發(fā)生異常時會轉(zhuǎn)到catch代碼塊中 while(true){//定義死循環(huán) Thread.sleep(400);//死循環(huán)中的線程每400ms激活一次 x+=0.1;//x=x+0.1 System.out.println("線程2:"+x);//在控制臺輸出x } } catch(InterruptedException e){}//當(dāng)try代碼塊有異常時轉(zhuǎn)到catch代碼塊 } } }
- 3)運行結(jié)果
總結(jié)
本文簡單介紹了Java中定時器和多線程編程的一些例子,大家可以在普通任務(wù)的基礎(chǔ)上嘗試進(jìn)行挑戰(zhàn)任務(wù),特別是將普通任務(wù)3修改為挑戰(zhàn)任務(wù)1。
以上為個人經(jīng)驗,希望能給大家一個參考,也希望大家多多支持腳本之家。
相關(guān)文章
springboot中的springSession的存儲和獲取實現(xiàn)
這篇文章主要介紹了springboot中的springSession的存儲和獲取實現(xiàn),文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2020-09-09關(guān)于RabbitMQ的Channel默認(rèn)線程
這篇文章主要介紹了關(guān)于RabbitMQ的Channel默認(rèn)線程,通過jvm工具觀察rabbitmq的線程使用情況,發(fā)現(xiàn)生產(chǎn)者每發(fā)一條消息,消費者這邊就會創(chuàng)建一條線程,言下之意,一個channel當(dāng)消息來到時就會異步處理這些消息,需要的朋友可以參考下2023-09-09Mybatis?XML配置文件實現(xiàn)增刪改查的示例代碼
本文主要介紹了Mybatis?XML配置文件實現(xiàn)增刪改查的示例代碼,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2025-03-03Java進(jìn)階核心之InputStream流深入講解
這篇文章主要給大家介紹了關(guān)于Java進(jìn)階核心之InputStream流的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧2021-02-02基于parameters參數(shù)實現(xiàn)參數(shù)化過程解析
這篇文章主要介紹了基于parameters參數(shù)實現(xiàn)參數(shù)化過程解析,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友可以參考下2020-08-08