偷偷摘套内射激情视频,久久精品99国产国产精,中文字幕无线乱码人妻,中文在线中文a,性爽19p

Java多線(xiàn)程程序設(shè)計(jì)初步

開(kāi)發(fā) 后端
多線(xiàn)程是為了使得多個(gè)線(xiàn)程并行的工作以完成多項(xiàng)任務(wù),以提高系統(tǒng)的效率。線(xiàn)程是在同一時(shí)間需要完成多項(xiàng)任務(wù)的時(shí)候被實(shí)現(xiàn)的,多線(xiàn)程程序是Java語(yǔ)言的一個(gè)很重要的特點(diǎn)。本文主要講述Java多線(xiàn)程程序設(shè)計(jì)。

在Java語(yǔ)言產(chǎn)生前,傳統(tǒng)的程序設(shè)計(jì)語(yǔ)言的程序同一時(shí)刻只能單任務(wù)操作,效率非常低,例如程序往往在接收數(shù)據(jù)輸入時(shí)發(fā)生阻塞,只有等到程序獲得數(shù)據(jù)后才能繼續(xù)運(yùn)行。 隨著Internet的迅猛發(fā)展,這種狀況越來(lái)越不能讓人們?nèi)淌埽喝绻W(wǎng)絡(luò)接收數(shù)據(jù)阻塞,后臺(tái)程序就處于等待狀態(tài)而不繼續(xù)任何操作,而這種阻塞是經(jīng)常會(huì)碰到的,此時(shí)CPU資源被白白的閑置起來(lái)。如果在后臺(tái)程序中能夠同時(shí)處理多個(gè)任務(wù),該多好??!應(yīng)Internet技術(shù)而生的Java語(yǔ)言解決了這個(gè)問(wèn)題,多線(xiàn)程程序是Java語(yǔ)言的一個(gè)很重要的特點(diǎn)。在一個(gè)Java程序中,我們可以同時(shí)并行運(yùn)行多個(gè)相對(duì)獨(dú)立的線(xiàn)程,例如,我們?nèi)绻麆?chuàng)建一個(gè)線(xiàn)程來(lái)進(jìn)行數(shù)據(jù)輸入輸出,而創(chuàng)建另一個(gè)線(xiàn)程在后臺(tái)進(jìn)行其它的數(shù)據(jù)處理,如果輸入輸出線(xiàn)程在接收數(shù)據(jù)時(shí)阻塞,而處理數(shù)據(jù)的線(xiàn)程仍然在運(yùn)行。多線(xiàn)程程序設(shè)計(jì)大大提高了程序執(zhí)行效率和處理能力。

線(xiàn)程的創(chuàng)建

我們知道Java是面向?qū)ο蟮某绦蛘Z(yǔ)言,用Java進(jìn)行程序設(shè)計(jì)就是設(shè)計(jì)和使用類(lèi),Java為我們提供了線(xiàn)程類(lèi)Thread來(lái)創(chuàng)建線(xiàn)程,創(chuàng)建線(xiàn)程與創(chuàng)建普通的類(lèi)的對(duì)象的操作是一樣的,而線(xiàn)程就是Thread類(lèi)或其子類(lèi)的實(shí)例對(duì)象。下面是一個(gè)創(chuàng)建啟動(dòng)一個(gè)線(xiàn)程的語(yǔ)句:

Thread thread1=new Thread(); file://聲明一個(gè)對(duì)象實(shí)例,即創(chuàng)建一個(gè)線(xiàn)程;

Thread1.run(); file://用Thread類(lèi)中的run()方法啟動(dòng)線(xiàn)程;

從這個(gè)例子,我們可以通過(guò)Thread()構(gòu)造方法創(chuàng)建一個(gè)線(xiàn)程,并啟動(dòng)該線(xiàn)程。事實(shí)上,啟動(dòng)線(xiàn)程,也就是啟動(dòng)線(xiàn)程的run()方法,而Thread類(lèi)中的run()方法沒(méi)有任何操作語(yǔ)句,所以這個(gè)線(xiàn)程沒(méi)有任何操作。要使線(xiàn)程實(shí)現(xiàn)預(yù)定功能,必須定義自己的run()方法。Java中通常有兩種方式定義run()方法:

通過(guò)定義一個(gè)Thread類(lèi)的子類(lèi),在該子類(lèi)中重寫(xiě)run()方法。Thread子類(lèi)的實(shí)例對(duì)象就是一個(gè)線(xiàn)程,顯然,該線(xiàn)程有我們自己設(shè)計(jì)的線(xiàn)程體run()方法,啟動(dòng)線(xiàn)程就啟動(dòng)了子類(lèi)中重寫(xiě)的run()方法。

通過(guò)Runnable接口,在該接口中定義run()方法的接口。所謂接口跟類(lèi)非常類(lèi)似,主要用來(lái)實(shí)現(xiàn)特殊功能,如復(fù)雜關(guān)系的多重繼承功能。在此,我們定義一個(gè)實(shí)現(xiàn)Runnable() 接口的類(lèi),在該類(lèi)中定義自己的run()方法,然后以該類(lèi)的實(shí)例對(duì)象為參數(shù)調(diào)用Thread類(lèi)的構(gòu)造方法來(lái)創(chuàng)建一個(gè)線(xiàn)程。

線(xiàn)程被實(shí)際創(chuàng)建后處于待命狀態(tài),激活(啟動(dòng))線(xiàn)程就是啟動(dòng)線(xiàn)程的run()方法,這是通過(guò)調(diào)用線(xiàn)程的start()方法來(lái)實(shí)現(xiàn)的。

下面一個(gè)例子實(shí)踐了如何通過(guò)上述兩種方法創(chuàng)建線(xiàn)程并啟動(dòng)它們:

// 通過(guò)Thread類(lèi)的子類(lèi)創(chuàng)建的線(xiàn)程;
    class thread1 extends Thread
     { file://自定義線(xiàn)程的run()方法;
      public void run()
       {
        System.out.println("Thread1 is running…");
       }
      }
    file://通過(guò)Runnable接口創(chuàng)建的另外一個(gè)線(xiàn)程;
   class thread2 implements Runnable
    { file://自定義線(xiàn)程的run()方法;
     public void run()
     {
      System.out.println("Thread2 is running…");
     }
    }
    file://程序的主類(lèi)'
    class Multi_Thread file://聲明主類(lèi);
     {
      plubic static void mail(String args[]) file://聲明主方法;
       {
        thread1 threadone=new thread1(); file://用Thread類(lèi)的子類(lèi)創(chuàng)建線(xiàn)程;
        Thread threadtwo=new Thread(new thread2()); file://用Runnable接口類(lèi)的對(duì)象創(chuàng)建線(xiàn)程;
        threadone.start(); threadtwo.start(); file://strat()方法啟動(dòng)線(xiàn)程;
       }
      }

運(yùn)行該程序就可以看出,線(xiàn)程threadone和threadtwo交替占用CPU,處于并行運(yùn)行狀態(tài)??梢钥闯?,啟動(dòng)線(xiàn)程的run()方法是通過(guò)調(diào)用線(xiàn)程的start()方法來(lái)實(shí)現(xiàn)的(見(jiàn)上例中主類(lèi)),調(diào)用start()方法啟動(dòng)線(xiàn)程的run()方法不同于一般的調(diào)用方法,調(diào)用一般方法時(shí),必須等到一般方法執(zhí)行完畢才能夠返回start()方法,而啟動(dòng)線(xiàn)程的run()方法后,start()告訴系統(tǒng)該線(xiàn)程準(zhǔn)備就緒可以啟動(dòng)run()方法后,就返回start()方法執(zhí)行調(diào)用start()方法語(yǔ)句下面的語(yǔ)句,這時(shí)run()方法可能還在運(yùn)行,這樣,線(xiàn)程的啟動(dòng)和運(yùn)行并行進(jìn)行,實(shí)現(xiàn)了多任務(wù)操作。

線(xiàn)程的優(yōu)先級(jí)

對(duì)于多線(xiàn)程程序,每個(gè)線(xiàn)程的重要程度是不盡相同,如多個(gè)線(xiàn)程在等待獲得CPU時(shí)間時(shí),往往我們需要優(yōu)先級(jí)高的線(xiàn)程優(yōu)先搶占到CPU時(shí)間得以執(zhí)行;又如多個(gè)線(xiàn)程交替執(zhí)行時(shí),優(yōu)先級(jí)決定了級(jí)別高的線(xiàn)程得到CPU的次數(shù)多一些且時(shí)間多長(zhǎng)一些;這樣,高優(yōu)先級(jí)的線(xiàn)程處理的任務(wù)效率就高一些。

Java中線(xiàn)程的優(yōu)先級(jí)從低到高以整數(shù)1~10表示,共分為10級(jí),設(shè)置優(yōu)先級(jí)是通過(guò)調(diào)用線(xiàn)程對(duì)象的setPriority()方法,如上例中,設(shè)置優(yōu)先級(jí)的語(yǔ)句為:

thread1 threadone=new thread1(); file://用Thread類(lèi)的子類(lèi)創(chuàng)建線(xiàn)程;
Thread threadtwo=new Thread(new thread2()); file://用Runnable接口類(lèi)的對(duì)象創(chuàng)建線(xiàn)程;
threadone.setPriority(6); file://設(shè)置threadone的優(yōu)先級(jí)6;
threadtwo.setPriority(3); file://設(shè)置threadtwo的優(yōu)先級(jí)3;
threadone.start(); threadtwo.start(); file://strat()方法啟動(dòng)線(xiàn)程;

這樣,線(xiàn)程threadone將會(huì)優(yōu)先于線(xiàn)程threadtwo執(zhí)行,并將占有更多的CPU時(shí)間。該例中,優(yōu)先級(jí)設(shè)置放在線(xiàn)程啟動(dòng)前,也可以在啟動(dòng)后進(jìn)行設(shè)置,以滿(mǎn)足不同的優(yōu)先級(jí)需求。

#p#

線(xiàn)程的(同步)控制

一個(gè)Java程序的多線(xiàn)程之間可以共享數(shù)據(jù)。當(dāng)線(xiàn)程以異步方式訪(fǎng)問(wèn)共享數(shù)據(jù)時(shí),有時(shí)候是不安全的或者不和邏輯的。比如,同一時(shí)刻一個(gè)線(xiàn)程在讀取數(shù)據(jù),另外一個(gè)線(xiàn)程在處理數(shù)據(jù),當(dāng)處理數(shù)據(jù)的線(xiàn)程沒(méi)有等到讀取數(shù)據(jù)的線(xiàn)程讀取完畢就去處理數(shù)據(jù),必然得到錯(cuò)誤的處理結(jié)果。這和我們前面提到的讀取數(shù)據(jù)和處理數(shù)據(jù)并行多任務(wù)并不矛盾,這兒指的是處理數(shù)據(jù)的線(xiàn)程不能處理當(dāng)前還沒(méi)有讀取結(jié)束的數(shù)據(jù),但是可以處理其它的數(shù)據(jù)。

如果我們采用多線(xiàn)程同步控制機(jī)制,等到***個(gè)線(xiàn)程讀取完數(shù)據(jù),第二個(gè)線(xiàn)程才能處理該數(shù)據(jù),就會(huì)避免錯(cuò)誤??梢?jiàn),線(xiàn)程同步是多線(xiàn)程編程的一個(gè)相當(dāng)重要的技術(shù)。

在講線(xiàn)程的同步控制前我們需要交代如下概念:

1. 用Java關(guān)鍵字synchonized同步對(duì)共享數(shù)據(jù)操作的方法

在一個(gè)對(duì)象中,用synchonized聲明的方法為同步方法。Java中有一個(gè)同步模型-監(jiān)視器,負(fù)責(zé)管理線(xiàn)程對(duì)對(duì)象中的同步方法的訪(fǎng)問(wèn),它的原理是:賦予該對(duì)象***一把'鑰匙',當(dāng)多個(gè)線(xiàn)程進(jìn)入對(duì)象,只有取得該對(duì)象鑰匙的線(xiàn)程才可以訪(fǎng)問(wèn)同步方法,其它線(xiàn)程在該對(duì)象中等待,直到該線(xiàn)程用wait()方法放棄這把鑰匙,其它等待的線(xiàn)程搶占該鑰匙,搶占到鑰匙的線(xiàn)程后才可得以執(zhí)行,而沒(méi)有取得鑰匙的線(xiàn)程仍被阻塞在該對(duì)象中等待。

file://聲明同步的一種方式:將方法聲明同步

class store
    {
     public synchonized void store_in()
     {
       ….
     }
     public synchonized void store_out(){
       ….}
     }

2.  利用wait()、notify()及notifyAll()方法發(fā)送消息實(shí)現(xiàn)線(xiàn)程間的相互聯(lián)系

Java程序中多個(gè)線(xiàn)程通過(guò)消息來(lái)實(shí)現(xiàn)互動(dòng)聯(lián)系的,這幾種方法實(shí)現(xiàn)了線(xiàn)程間的消息發(fā)送。例如定義一個(gè)對(duì)象的synchonized 方法,同一時(shí)刻只能夠有一個(gè)線(xiàn)程訪(fǎng)問(wèn)該對(duì)象中的同步方法,其它線(xiàn)程被阻塞。通常可以用notify()或notifyAll()方法喚醒其它一個(gè)或所有線(xiàn)程。而使用wait()方法來(lái)使該線(xiàn)程處于阻塞狀態(tài),等待其它的線(xiàn)程用notify()喚醒。

一個(gè)實(shí)際的例子就是生產(chǎn)和銷(xiāo)售,生產(chǎn)單元將產(chǎn)品生產(chǎn)出來(lái)放在倉(cāng)庫(kù)中,銷(xiāo)售單元?jiǎng)t從倉(cāng)庫(kù)中提走產(chǎn)品,在這個(gè)過(guò)程中,銷(xiāo)售單元必須在倉(cāng)庫(kù)中有產(chǎn)品時(shí)才能提貨;如果倉(cāng)庫(kù)中沒(méi)有產(chǎn)品,則銷(xiāo)售單元必須等待。

程序中,假如我們定義一個(gè)倉(cāng)庫(kù)類(lèi)store,該類(lèi)的實(shí)例對(duì)象就相當(dāng)于倉(cāng)庫(kù),在store類(lèi)中定義兩個(gè)成員方法:store_in(),用來(lái)模擬產(chǎn)品制造者往倉(cāng)庫(kù)中添加產(chǎn)品;strore_out()方法則用來(lái)模擬銷(xiāo)售者從倉(cāng)庫(kù)中取走產(chǎn)品。然后定義兩個(gè)線(xiàn)程類(lèi):customer類(lèi),其中的run()方法通過(guò)調(diào)用倉(cāng)庫(kù)類(lèi)中的store_out()從倉(cāng)庫(kù)中取走產(chǎn)品,模擬銷(xiāo)售者;另外一個(gè)線(xiàn)程類(lèi)producer中的run()方法通過(guò)調(diào)用倉(cāng)庫(kù)類(lèi)中的store_in()方法向倉(cāng)庫(kù)添加產(chǎn)品,模擬產(chǎn)品制造者。在主類(lèi)中創(chuàng)建并啟動(dòng)線(xiàn)程,實(shí)現(xiàn)向倉(cāng)庫(kù)中添加產(chǎn)品或取走產(chǎn)品。

如果倉(cāng)庫(kù)類(lèi)中的store_in() 和store_out()方法不聲明同步,這就是個(gè)一般的多線(xiàn)程,我們知道,一個(gè)程序中的多線(xiàn)程是交替執(zhí)行的,運(yùn)行也是無(wú)序的,這樣,就可能存在這樣的問(wèn)題:

倉(cāng)庫(kù)中沒(méi)有產(chǎn)品了,銷(xiāo)售者還在不斷光顧,而且還不停的在'取'產(chǎn)品,這在現(xiàn)實(shí)中是不可思義的,在程序中就表現(xiàn)為負(fù)值;如果將倉(cāng)庫(kù)類(lèi)中的stroe_in()和store_out()方法聲明同步,如上例所示:就控制了同一時(shí)刻只能有一個(gè)線(xiàn)程訪(fǎng)問(wèn)倉(cāng)庫(kù)對(duì)象中的同步方法;即一個(gè)生產(chǎn)類(lèi)線(xiàn)程訪(fǎng)問(wèn)被聲明為同步的store_in()方法時(shí),其它線(xiàn)程將不能夠訪(fǎng)問(wèn)對(duì)象中的store_out()同步方法,當(dāng)然也不能訪(fǎng)問(wèn)store_in()方法。必須等到該線(xiàn)程調(diào)用wait()方法放棄鑰匙,其它線(xiàn)程才有機(jī)會(huì)訪(fǎng)問(wèn)同步方法。

這個(gè)原理實(shí)際中也很好理解,當(dāng)生產(chǎn)者(producer)取得倉(cāng)庫(kù)***的鑰匙,就向倉(cāng)庫(kù)中添放產(chǎn)品,此時(shí)其它的銷(xiāo)售者(customer,可以是一個(gè)或多個(gè))不可能取得鑰匙,只有當(dāng)生產(chǎn)者添放產(chǎn)品結(jié)束,交還鑰匙并且通知銷(xiāo)售者,不同的銷(xiāo)售者根據(jù)取得鑰匙的先后與否決定是否可以進(jìn)入倉(cāng)庫(kù)中提走產(chǎn)品。

【編輯推薦】

  1. 如何用Java實(shí)現(xiàn)FTP服務(wù)器
  2. Java以外的選擇 Scala編程語(yǔ)言簡(jiǎn)介
  3. 通過(guò)Java編程處理XML服務(wù)定義
責(zé)任編輯:楊鵬飛 來(lái)源: yesky
相關(guān)推薦

2010-09-17 09:08:49

Java多線(xiàn)程

2011-04-18 09:22:38

多線(xiàn)程

2013-12-12 16:30:20

Lua腳本語(yǔ)言

2009-06-29 15:25:00

Java多線(xiàn)程

2011-08-22 17:41:23

LUA 腳本 語(yǔ)言

2011-08-31 16:22:51

LUA多線(xiàn)程

2011-06-22 14:30:44

QT 多線(xiàn)程 線(xiàn)程

2010-09-25 13:47:14

Java跨平臺(tái)

2013-05-23 15:59:00

線(xiàn)程池

2011-07-22 13:41:57

java

2011-07-04 13:31:15

2010-03-15 19:47:30

Java多線(xiàn)程程序

2009-12-04 10:53:06

VS WEB

2010-12-28 10:12:39

PHP

2019-09-26 10:19:27

設(shè)計(jì)電腦Java

2009-06-22 14:03:00

java教材程序設(shè)計(jì)

2012-05-02 13:22:46

JavaJava設(shè)計(jì)

2009-03-12 10:52:43

Java線(xiàn)程多線(xiàn)程

2010-03-17 18:14:45

Java多線(xiàn)程程序

2017-09-05 08:16:29

代碼判斷函數(shù)
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號(hào)