Mison(邁勝)
BlogJava
::
首頁(yè)
::
新隨筆
::
聯(lián)系
::
聚合
::
管理
posts - 7, comments - 0, trackbacks - 0
<
2010年2月
>
日
一
二
三
四
五
六
31
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
1
2
3
4
5
6
7
8
9
10
11
12
13
常用鏈接
我的隨筆
我的評(píng)論
我的參與
留言簿
給我留言
查看公開(kāi)留言
查看私人留言
隨筆檔案
2010年3月 (2)
2010年2月 (5)
文章檔案
2010年2月 (2)
搜索
最新評(píng)論
閱讀排行榜
1.?Maven2.2.1下載(247)
2.?SCWCD認(rèn)證之路(229)
3.?創(chuàng)建線程兩種方式的比較(190)
4.?MyEclipse卡機(jī)問(wèn)題的解決(134)
5.?新鮮出爐的10年福富筆試(130)
評(píng)論排行榜
1.?2010年的技術(shù)架構(gòu)建議(0)
2.?【Black設(shè)計(jì)模式】觀察者模式代碼解析(0)
3.?Maven2.2.1下載(0)
4.?新鮮出爐的10年福富筆試(0)
5.?創(chuàng)建線程兩種方式的比較(0)
創(chuàng)建線程兩種方式的比較
裝載:Mison(邁勝)
http://bbs.misonsoft.com/thread-1225-1-2.html
通過(guò)鐵路售票程序來(lái)理解實(shí)現(xiàn)多線程的兩種方法:通過(guò)java.lang.Thread類和通過(guò)Runnable接口
java中有兩種實(shí)現(xiàn)多線程的方式。一是直接繼承Thread類,二是實(shí)現(xiàn)Runnable接口。那么這兩種實(shí)現(xiàn)多線程的方式在應(yīng)用上有什么區(qū)別呢?
為了回答這個(gè)問(wèn)題,我們可以通過(guò)編寫(xiě)一段代碼來(lái)進(jìn)行分析。我們用代碼來(lái)模擬鐵路售票系統(tǒng),實(shí)現(xiàn)通過(guò)四個(gè)售票點(diǎn)發(fā)售某日某次列車的100張車票,一個(gè)售票點(diǎn)用一個(gè)線程表示。
我們首先這樣編寫(xiě)這個(gè)程序:
public
class
ThreadDome1
{
public
static
void
main(String[] args)
{
ThreadTest t
=
new
ThreadTest();
t.start();
t.start();
t.start();
t.start();
}
}
class
ThreadTest
extends
Thread
{
private
int
ticket
=
100
;
public
void
run()
{
while
(
true
)
{
if
(ticket
>
0
)
{
System.out.println(Thread.currentThread().getName()
+
"
is saling ticket
"
+
ticket
--
);
}
else
{
break
;
}
}
}
}
上面的代碼中,我們用ThreadTest類模擬售票處的售票過(guò)程,run方法中的每一次循環(huán)都將總票數(shù)減1,模擬賣出一張車票,同時(shí)該車票號(hào)打印出來(lái),直接剩余的票數(shù)到零為止。在ThreadDemo1類的main方法中,我們創(chuàng)建了一個(gè)線程對(duì)象,并重復(fù)啟動(dòng)四次,希望通過(guò)這種方式產(chǎn)生四個(gè)線程。從運(yùn)行的結(jié)果來(lái)看我們發(fā)現(xiàn)其實(shí)只有一個(gè)線程在運(yùn)行,這個(gè)結(jié)果告訴我們:一個(gè)線程對(duì)象只能啟動(dòng)一個(gè)線程,無(wú)論你調(diào)用多少遍start()方法,結(jié)果只有一個(gè)線程。
我們接著修改ThreadDemo1,在main方法中創(chuàng)建四個(gè)Thread對(duì)象:
public
class
ThreadDemo1
{
public
static
void
main(String[] args)
{
new
ThreadTest().start();
new
ThreadTest().start();
new
ThreadTest().start();
new
ThreadTest().start();
}
}
class
ThreadTest
extends
Thread
{
private
int
ticket
=
100
;
public
void
run()
{
while
(
true
)
{
if
(ticket
>
0
)
{
System.out.println(Thread.currentThread().getName()
+
"
is saling ticket
"
+
ticket
--
);
}
else
{
break
;
}
}
}
}
這下達(dá)到目的了嗎?
從結(jié)果上看每個(gè)票號(hào)都被打印了四次,即四個(gè)線程各自賣各自的100張票,而不去賣共同的100張票。這種情況是怎么造成的呢?我們需要的是,多個(gè)線程去處理同一個(gè)資源,一個(gè)資源只能對(duì)應(yīng)一個(gè)對(duì)象,在上面的程序中,我們創(chuàng)建了四個(gè)ThreadTest對(duì)象,就等于創(chuàng)建了四個(gè)資源,每個(gè)資源都有100張票,每個(gè)線程都在獨(dú)自處理各自的資源。
經(jīng)過(guò)這些實(shí)驗(yàn)和分析,可以總結(jié)出,要實(shí)現(xiàn)這個(gè)鐵路售票程序,我們只能創(chuàng)建一個(gè)資源對(duì)象,但要?jiǎng)?chuàng)建多個(gè)線程去處理同一個(gè)資源對(duì)象,并且每個(gè)線程上所運(yùn)行的是相同的程序代碼。在回顧一下使用接口編寫(xiě)多線程的過(guò)程。
public
class
ThreadDemo1
{
public
static
void
main(String[] args)
{
ThreadTest t
=
new
ThreadTest();
new
Thread(t).start();
new
Thread(t).start();
new
Thread(t).start();
new
Thread(t).start();
}
}
class
ThreadTest
implements
Runnable
{
private
int
tickets
=
100
;
public
void
run()
{
while
(
true
)
{
if
(tickets
>
0
)
{
System.out.println(Thread.currentThread().getName()
+
"
is saling ticket
"
+
tickets
--
);
}
}
}
}
上面的程序中,創(chuàng)建了四個(gè)線程,每個(gè)線程調(diào)用的是同一個(gè)ThreadTest對(duì)象中的run()方法,訪問(wèn)的是同一個(gè)對(duì)象中的變量(tickets)的實(shí)例,這個(gè)程序滿足了我們的需求。在Windows上可以啟動(dòng)多個(gè)記事本程序一樣,也就是多個(gè)進(jìn)程使用同一個(gè)記事本程序代碼。
可見(jiàn),實(shí)現(xiàn)Runnable接口相對(duì)于繼承Thread類來(lái)說(shuō),有如下顯著的好處:
(1)適合多個(gè)相同程序代碼的線程去處理同一資源的情況,把虛擬CPU(線程)同程序的代碼,數(shù)據(jù)有效的分離,較好地體現(xiàn)了面向?qū)ο蟮脑O(shè)計(jì)思想。
(2)可以避免由于
Java
的單繼承特性帶來(lái)的局限。我們經(jīng)常碰到這樣一種情況,即當(dāng)我們要將已經(jīng)繼承了某一個(gè)類的子類放入多線程中,由于一個(gè)類不能同時(shí)有兩個(gè)父類,所以不能用繼承Thread類的方式,那么,這個(gè)類就只能采用實(shí)現(xiàn)Runnable接口的方式了。
(3)有利于程序的健壯性,代碼能夠被多個(gè)線程共享,代碼與數(shù)據(jù)是獨(dú)立的。當(dāng)多個(gè)線程的執(zhí)行代碼來(lái)自同一個(gè)類的實(shí)例時(shí),即稱它們共享相同的代碼。多個(gè)線程操作相同的數(shù)據(jù),與它們的代碼無(wú)關(guān)。當(dāng)共享訪問(wèn)相同的對(duì)象時(shí),即它們共享相同的數(shù)據(jù)。當(dāng)線程被構(gòu)造時(shí),需要的代碼和數(shù)據(jù)通過(guò)一個(gè)對(duì)象作為構(gòu)造函數(shù)實(shí)參傳遞進(jìn)去,這個(gè)對(duì)象就是一個(gè)實(shí)現(xiàn)了Runnable接口的類的實(shí)例。
posted on 2010-02-23 09:19
Mison
閱讀(190)
評(píng)論(0)
編輯
收藏
新用戶注冊(cè)
刷新評(píng)論列表
只有注冊(cè)用戶
登錄
后才能發(fā)表評(píng)論。
網(wǎng)站導(dǎo)航:
博客園
IT新聞
Chat2DB
C++博客
博問(wèn)
管理
Powered by:
BlogJava
Copyright ©2025 Mison
主站蜘蛛池模板:
宁都县
|
永胜县
|
石台县
|
敦化市
|
高陵县
|
屏东市
|
泸州市
|
泾川县
|
庐江县
|
怀来县
|
仙桃市
|
日喀则市
|
修武县
|
洪雅县
|
乡城县
|
周至县
|
南华县
|
麻江县
|
泸州市
|
南安市
|
阿巴嘎旗
|
河北省
|
嘉黎县
|
株洲市
|
平阳县
|
高雄县
|
伊川县
|
翁牛特旗
|
美姑县
|
舞钢市
|
拜城县
|
武穴市
|
黄骅市
|
新化县
|
荣成市
|
浪卡子县
|
合山市
|
达日县
|
大厂
|
晋中市
|
佳木斯市
|