<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    我的隱式生活(My Implicit Life)

    繼續(xù)搞“對(duì)象”,玩OO.

    首頁 新隨筆 聯(lián)系 聚合 管理
      11 Posts :: 1 Stories :: 39 Comments :: 0 Trackbacks

    關(guān)鍵字:Observer PatternJava ThreadJava Swing Application

    1 近來的閱讀

    近來寒暑不常,希自珍慰。武漢天氣不是狂冷,就是狂熱,不時(shí)還給我整個(gè)雪花,就差冰雹了。

     

    自己做的事吧,也沒有什么勁兒。看看自己喜歡的東西,等著希望中的學(xué)校能給我offers(是復(fù)數(shù)),看著自己想去又不想去的公司的未來同事在群里面幻想未來的樣子,別操你大爺了,都成人這么久了,咋就還不了解這個(gè)世道呢?你給老板賺十塊錢,老板自然會(huì)給你一塊。如果老板的周圍會(huì)賺錢的人不多,你還可以嘗試吆喝更高的價(jià)錢。就這么個(gè)事,幻想有個(gè)鳥用。還不如靜下心來好好學(xué)點(diǎn)兒東西,想想將來怎么多多給老板賺錢。無論以后打工還是自己當(dāng)老板,路都得這么走出來。

     

    另外,就是思考的畢設(shè)的事情。畢竟,讓我立刻狠心的fuck掉這個(gè)學(xué)位也是不現(xiàn)實(shí)的。所以,繼續(xù)搞,搞一個(gè)題目叫做“基于復(fù)雜網(wǎng)絡(luò)的可度量防垃圾郵件系統(tǒng)”的論文加實(shí)驗(yàn)系統(tǒng)。看名字很BT,可我覺得這已經(jīng)是我覺得最有意思的畢設(shè)題目了。我一定要做出點(diǎn)東西來。

     

    無聊看書加上要完成畢設(shè)的實(shí)驗(yàn)系統(tǒng),于是有了些動(dòng)力,就產(chǎn)生了本篇小隨筆。權(quán)當(dāng)備忘吧。

     

    看著“觀察者模式”,琢磨琢磨,感覺跟別的模式有那么一點(diǎn)不一樣。但是又說不出來,感覺使用這個(gè)模式的環(huán)境,為多線程為多。然后,就轉(zhuǎn)而去看線程的書,看著線程的書,又發(fā)現(xiàn)畢設(shè)要用的Swing是學(xué)習(xí)理解線程很好的素材,而且Swing中的event-dispatch機(jī)制就是“觀察者模式”,于是又轉(zhuǎn)而去看講Swing的書及專欄文章。

     

    到此,這3個(gè)東西是徹底扯在一起了。總結(jié)一下它們之間的關(guān)系:Swing是建立在event-dispatch機(jī)制及Swing Single Thread下的多線程GUI編程環(huán)境。當(dāng)然,在很多情況下,你寫Swing也不大會(huì)用到(察覺)多線程(如我們的java課本中的Swing例子),但是,使用它的可能性已經(jīng)大大增加了。而且要寫好Swing,不理解線程是很困難的。

    2 Java Thread

    2.1 操作系統(tǒng)及面向過程

    對(duì)于我這個(gè)新手來講,使用多線程的機(jī)會(huì)不多。天天搞J2EE的應(yīng)用開發(fā),也根本用不上這個(gè)東西。但是,不理解你,不使用你,何談功力的提升呢。你不找我,我也要找你。

     

    在面向?qū)ο蟮氖澜缰校@個(gè)Thread讓我真的不好理解。它仿佛和我們自己寫的對(duì)象,JDK的別的API類庫都不一樣,咋一看,看不出它的“使用價(jià)值”。(我理解的對(duì)象都有很“明顯”的“使用價(jià)值”,呵呵)。

     

    因?yàn)楦嗟卣務(wù)摗斑M(jìn)程”、“線程”還是在操作系統(tǒng)層面,記得在OS課本中有好幾個(gè)章節(jié)都是講“進(jìn)程”相關(guān)的知識(shí):調(diào)度算法、調(diào)度隊(duì)列、調(diào)度優(yōu)先級(jí)等等。后來上UnixLinux的時(shí)候重點(diǎn)更是folk和進(jìn)程間通訊(IPC)機(jī)制。但都是停留在理論理解,應(yīng)付考試的階段。而且編寫的代碼也都是面向過程的風(fēng)格,沒有“對(duì)象”的感覺。

     

    Java能把OS層的概念加進(jìn)來并予以實(shí)現(xiàn),功能上很強(qiáng),另外也給新手接觸底層編程的機(jī)會(huì)。但是,把OS層的線程概念及它的面向過程編寫風(fēng)格與面向?qū)ο笃毡榈娘L(fēng)格一比較,對(duì)Java Thread對(duì)象的理解就有點(diǎn)迷糊了。

    2.2 從接口的本質(zhì)思考

    一般寫程序不會(huì)太關(guān)注main(),特別是J2EE的東西搞多了,更是把它給忘盡了。main是程序的開始,是JVM的主線程。線程是另一個(gè)main(這樣理解肯定不準(zhǔn)確,但是有極大雷同),是欲并行執(zhí)行的程序代碼序列。

     

    java中,如果在main之外,還要執(zhí)行獨(dú)立并行的程序代碼序列,就要用到java線程了。方法也比較簡單:把獨(dú)立執(zhí)行的代碼序列寫到一個(gè)Runnable對(duì)象的run方法中,然后在父進(jìn)程(很有可能就是main線程)start它(先要把Runnable變成Thread對(duì)象)就可以了。

     

    接口描述的是一種功能,而不是事物本質(zhì)(類來描述)。如果我們把“能獨(dú)立并行執(zhí)行”當(dāng)作一個(gè)對(duì)象的能力的話,把線程概念融入面向?qū)ο缶腿菀锥嗔恕F鸫a我是這么理解的。

     

    至于你是喜歡給已有的類添加一個(gè)這個(gè)功能(也就是讓已有的類來實(shí)現(xiàn)Runnable接口),還是另外專門寫一個(gè)類,專門封裝這種功能。就見仁見智了。正如我都喜歡把main獨(dú)立寫在一個(gè)控制類中,而不是放在功能類中一樣。

    2.3 匿名的嵌套類

    也正是因?yàn)榫€程的并行性本質(zhì),在我們的代碼中,那里要并行執(zhí)行,我們就在這里開一個(gè)新的線程。而這時(shí),為了最簡便,對(duì)代碼結(jié)構(gòu)影響最小,最常見方式的就是開一個(gè)匿名的嵌套線程。

    例子:如果doNoSequence()需要并行于執(zhí)行doJob()的線程而獨(dú)立執(zhí)行。

     1Void doJob(){
     2
     3    doFirst();
     6
     7    //need to be excuted in concurrently. 
     9    doNoSequence();
    11 
    13    doSecond();
    14
    15}

    16

     

    就可以為它開一個(gè)匿名的嵌套線程。

     1Void doJob(){
     2    doFirst();
     3    
     4    new Thread(){
     5    public void run() {
     6    doNoSequence();
     7    }

     8    }
    .start();
     9
    10    doSecond();
    11}

    12

     

    2.4 異步的本質(zhì),同步的需要


    “獨(dú)立并行”的感覺一般開始都很好,至于以后,呵呵,不好說。

     

    特別是當(dāng)系統(tǒng)已經(jīng)設(shè)計(jì)好了以后,在代碼中按上面的例子隨便開新線程。看似操作容易,但如果開的線程一多,相互之間的聯(lián)系一多,以后就很難理解、管理和維護(hù)(許多article作者的話,我沒有經(jīng)驗(yàn))。

     

    doNoSequence()現(xiàn)在就開始難受了,因?yàn)樗l(fā)現(xiàn)它和主線程還有很多聯(lián)系,如和doFirst()有共同access的對(duì)象;還如doSecond()接受它返回的參數(shù),一定要等它返回才能繼續(xù)執(zhí)行(也就是doNoSequence()對(duì)于主線程是block的)。明顯,這里都需要“同步”。

     

    當(dāng)然,也不必絕望,只不過在代碼里面繼續(xù)添加更多的我不熟練的線程控制代碼。線程開的越多,線程有關(guān)的關(guān)鍵字和控制代碼就會(huì)出現(xiàn)的更多。最終的代碼也許會(huì)面目全非,越來越難看出核心邏輯了。線程代碼多了是小,但是核心的業(yè)務(wù)邏輯被淹沒了是不允許的。

     

    最好的解決方法,當(dāng)然就是在設(shè)計(jì)的時(shí)候,多考慮一下程序并行化的可能。把有可能并行的邏輯分開來寫。換句話講,也就是要增加并行程序內(nèi)部的耦合性,降低并行程序之間的耦合性。以便將來并不并行都容易使用。

     

    如要編寫既能異步執(zhí)行,又能相對(duì)容易實(shí)現(xiàn)同步控制的代碼,不少人(當(dāng)然,都是大牛人)推薦使用“觀察者模式”來重構(gòu)你的系統(tǒng)。

    3 觀察者模式

    “觀察者模式(Observer Pattern)”是一個(gè)好東西,我以前實(shí)在是太孤陋寡聞了,竟然沒有好好的去了解這樣一個(gè)被廣泛使用的模式,它給我?guī)砗芏嗟乃伎肌Mㄟ^它,使我更容易理解很多框架,資料,文章,代碼。因?yàn)椋?dāng)我一看到listenereventobserver等詞語,就知道其設(shè)計(jì)原型為“觀察者模式”。

     

    “觀察者模式”通過定義抽象主題[Abstrsct Subject](也叫消息源[Message Source]、事件源[Evnet Source]、被觀察者),抽象觀察者[Abstract Observer](更多的叫監(jiān)聽者[listener]),及它們之間的所謂事件[Event](也叫消息[Message])來實(shí)現(xiàn)的。這里的事件其實(shí)是對(duì)被觀察者和觀察者之間傳遞信息的一個(gè)封裝,如果你覺得沒有必要封裝什么,那你用個(gè)Stringint傳遞信息也是可以的。

     

    自己再寫兩個(gè)類實(shí)現(xiàn)(Implement)上面兩個(gè)抽象類就完成了一個(gè)“觀察者模式”。

     

    下面嘗試舉例說明,想必大家都經(jīng)常被各種垃圾短信所困擾,一般這些短信都是推薦你去訂閱一些服務(wù),如每日一警句,足球彩票預(yù)測,色情資訊等等。如果你按照上面的number回了信息,就等于訂閱了,也就要付錢了。為了防止你過分反感這個(gè)例子,影響敘述,那我就找個(gè)稍微有用那么一點(diǎn)的短信訂閱服務(wù)來舉例――“天氣預(yù)報(bào)”。

     

    提供服務(wù)的“天氣預(yù)報(bào)提供商”就是模式中的“被觀察者”,而訂閱了服務(wù)的“訂閱者”就是模式中的“觀察者”。“天氣預(yù)報(bào)服務(wù)商啊,我已經(jīng)訂閱你的天氣服務(wù)啦,我盯上你啦,你一旦有了明天的天氣情況就要及時(shí)通知我哦!”――這樣粗俗的描述或許會(huì)讓你更加容易理解,為什么天氣預(yù)報(bào)服務(wù)商被稱為“被觀察者”,而我們被稱為“觀察者”,而我們之間傳遞的信息就是天氣情況。

     

    例子的類圖:

    o_swing_1.JPG 


    模擬訂閱及發(fā)送天氣預(yù)報(bào)的代碼:

     1package gs.blogExample.weatherService;
     2
     3public class SimulatedEnvironment {
     4    public static void main(String[] args) {
     5
     6        //定義天氣服務(wù)提供商(模式角色:被觀察者)
     7        WeatherServiceProvider myProvider = new WeatherServiceProvider();
     8
     9        //定義兩個(gè)天氣服務(wù)訂閱者(模式角色:觀察者)
    10        Housewife hw = new Housewife();
    11        BusDriver bd = new BusDriver();
    12
    13        //他們訂閱天氣服務(wù)
    14        myProvider.addServiceListener(hw);
    15        myProvider.addServiceListener(bd);
    16        
    17        System.out.println("<<Date:2005-3-12>>");
    18        //天氣服務(wù)提供商得到了新的天氣信息,武漢今天9度
    19        //只要天氣服務(wù)商得到了任何一個(gè)城市的新天氣,就會(huì)通知訂閱者
    20        myProvider.setNewWeather(new Weather("WUHAN",9,10));
    21
    22        //housewife退訂天氣服務(wù)
    23        myProvider.removeServiceListener(hw);
    24        
    25        System.out.println("<<Date:2005-3-13>>");
    26        //第二天,天氣供應(yīng)商又得到了新的信息,武漢今天35度
    27        //武漢一天之間從9度變35度,是可信的
    28        myProvider.setNewWeather(new Weather("WUHAN",35,36));
    29    }

    30}

    31

     

    模擬輸出的結(jié)果如下:

    <<Date:2005-3-12>>

    Housewife receiving weatherInfo begins..........

    Housewife said: “so cool,let's make huoguo!!”

    Housewife receiving weatherInfo ended..........

    BusDriver receiving weatherInfo begins..........

    BusDriver said: “fine day,nothing to do.”

    BusDriver receiving weatherInfo ended..........

    <<Date:2005-3-13>>

    BusDriver receiving weatherInfo begins..........

    BusDriver said: “so hot,open air condition!!”

    BusDriver receiving weatherInfo ended..........

    說明:訂閱者接到天氣預(yù)報(bào)后的行為就是“隨便打印一句感受”。也就是說,例子中訂閱者Print出一句話就代表他收到天氣預(yù)報(bào)了。

     

    從上面的輸出結(jié)果可以看到,當(dāng)Housewife2005-3-12號(hào)退訂了天氣服務(wù)。的確,第二天天氣預(yù)報(bào)提供商就沒有再給它提供服務(wù)了。

     

    繼續(xù)拓展這個(gè)系統(tǒng),使之提供另一種服務(wù)――“足球貼士服務(wù)”,根據(jù)“觀察者模式”的角色,添加“足球貼士提供商”(被觀察者)、“足球貼士訂閱者”(觀察者)和事件類“足球貼士事件”,另還有一個(gè)輔助描述具體足球貼士信息的類“足球貼士信息”。

     

    繼續(xù)類圖:

    o_swing_2.jpg 


    模擬發(fā)送接受天氣預(yù)報(bào)和足球貼士的代碼:

     1package gs.blogExample.weatherService;
     2
     3public class SimulatedEnvironment {
     4    public static void main(String[] args) {
     5
     6        //定義天氣服務(wù)提供商(模式角色:被觀察者)
     7        WeatherServiceProvider weatherServiceProvider = new WeatherServiceProvider();
     8
     9        //定義天氣服務(wù)提供商(模式角色:被觀察者)
    10        SoccerTipServiceProvider soccerTipServiceProvider = new SoccerTipServiceProvider();
    11
    12        //定義兩個(gè)天氣服務(wù)訂閱者(模式角色:觀察者)
    13        Housewife hw = new Housewife();
    14        BusDriver bd = new BusDriver();
    15
    16        //hw、bd都訂閱天氣服務(wù),bd還訂閱了足球貼士服務(wù)
    17        weatherServiceProvider.addServiceListener(hw);
    18        weatherServiceProvider.addServiceListener(bd);
    19        soccerTipServiceProvider.addServiceListener(bd);
    20
    21        System.out.println("<<Date:2005-3-12>>");
    22        //天氣服務(wù)提供商得到了新的天氣信息,武漢今天9度
    23        //足球貼士提供商得到了新的預(yù)測信息,MAN VS ASL 預(yù)測是1
    24        weatherServiceProvider.setNewWeather(new Weather("WUHAN",9,10));
    25        soccerTipServiceProvider.setNewSoccerTip(new SoccerTip("MAN VS ASL","2005-4-5","1"));
    26
    27        //housewife退訂天氣服務(wù)
    28        weatherServiceProvider.removeServiceListener(hw);
    29
    30        System.out.println("<<Date:2005-3-13>>");
    31        //第二天,天氣供應(yīng)商又得到了新的信息,武漢今天35度
    32        weatherServiceProvider.setNewWeather(new Weather("WUHAN",35,36));
    33    }

    34}

    35

     

    模擬輸出的結(jié)果如下:

    <<Date:2005-3-12>>

    Housewife receiving weatherInfo begins..........

    Housewife said: "so cool,let's make huoguo!!"

    Housewife receiving weatherInfo ended..........

    BusDriver receiving weatherInfo begins..........

    BusDriver said: "fine day,nothing to do."

    BusDriver receiving weatherInfo ended..........

    BusDriver receiving soccerTip begins..........

    BusDriver said: "I am about to buy soccer lottery!!!I want to be rich!"

    BusDriver receiving soccerTip ended..........

    <<Date:2005-3-13>>

    BusDriver receiving weatherInfo begins..........

    BusDriver said: "so hot,open air condition!!"

    BusDriver receiving weatherInfo ended..........

     

    源碼下載(JBuilder Project)

    3.1 天生的異步模型 

     1 private void sendWeatherService() {
     2
     3        WeatherEvent we = new WeatherEvent(this.cityWeather);
     4
     5        Vector cloneListenerList = (Vector) getListenerList().clone();
     6        Iterator iter = cloneListenerList.iterator();
     7        while (iter.hasNext()) {
     8            WeatherServiceListener listener =
     9                    (WeatherServiceListener) iter.next();
    10            listener.WeatherArrived(we);
    11        }

    12
    13}

    14


    繼續(xù)上面的例子,天氣預(yù)報(bào)提供商為訂閱者發(fā)送天氣預(yù)報(bào)的行為被封裝在sendWeatherService方法中,而天氣預(yù)報(bào)訂閱者接受到天氣預(yù)報(bào)信息后的行為被封裝在WeatherArrived方法中。

     

    從上面天氣預(yù)報(bào)提供商的sendWeatherService方法的代碼可以看到,提供商會(huì)遍歷所有WeatherListener,然后通過調(diào)用它們的WeatherArrived方法來向它們傳遞WeatherEvent事件。

     

    在這里,兩個(gè)方法是在一個(gè)線程中運(yùn)行的,也就是說,對(duì)于天氣提供商來講,如果第一個(gè)listenerWeatherArrived方法沒有返回,那它就沒有辦法通知第二個(gè)listener

     

    具體到我們這個(gè)例子,我們是先通知Housewife再通知BusDriver的(由于遍歷順序的原因),也就是說是先執(zhí)行HousewifeWeatherArrived方法,再執(zhí)行BusDriverWeatherArrived方法。試想,如果HousewifeWeatherArrived方法中要做的事情很多(往往家庭主婦就是如此),長期得不到返回,那么BusDriverWeatherArrived方法就長期得不到執(zhí)行,也就是說BusDriver長期得不到天氣消息。對(duì)于天氣這種時(shí)效性很強(qiáng)的信息,很明顯,這樣不行。是Bug

     

    自然的,可以運(yùn)用Java Thraed,考慮把listener們的WeatherArrived并行化,放在不同的線程里去執(zhí)行。這樣,每當(dāng)通知第一個(gè)listener都不會(huì)阻塞通知下一個(gè)listener

     

    的確,無論用不用觀察者模式,你加幾行java線程代碼都可以實(shí)現(xiàn)并行化。只是,“觀察者模式”無論在構(gòu)思理解層面上,還是代碼結(jié)構(gòu)上,都特別容易向并行化過渡。

     

    為什么這面說?一句話講:“觀察者模式”中的“被觀察者角色”和“觀察者角色”本生內(nèi)在就有強(qiáng)烈的并行性特征。擁有“觀察者模式”的系統(tǒng)一般都有這個(gè)特性,而有這個(gè)特性的系統(tǒng)也一般也可以設(shè)計(jì)成“觀察者模式”。

    3.2 設(shè)計(jì)并行系統(tǒng)的好方法

    Messge機(jī)制或Event機(jī)制(以“觀察者模式”原型)來設(shè)計(jì)系統(tǒng),可以更好的適應(yīng)一旦程序有多線程的需要。因?yàn)樵凇坝^察者模式”中,我們?cè)诙x角色及事件時(shí),其實(shí)它們已有并行的特征(也就是多線程的可能)。

     

    這樣可以讓我們?cè)O(shè)計(jì)系統(tǒng)的時(shí)候,暫時(shí)不把主要的腦神經(jīng)拿去考慮線程的復(fù)雜問題,放心的先把系統(tǒng)涉及的對(duì)象設(shè)計(jì)出來。而后來一旦有了線程化的需要,可以相對(duì)方便、清晰的添加,也不會(huì)出現(xiàn)太“拗眼”的代碼群。

     

    結(jié)論還是,有利于系統(tǒng)的清晰,維護(hù)的方便。

     

    Swing應(yīng)用程序的設(shè)計(jì)中,就有人這樣設(shè)計(jì),并且把它上升為一種通用方法,可參見下面的Event-Dispatch方法章節(jié)。

    4 Java Swing

    SwingJavaGUI類庫。因此,Java的桌面應(yīng)用程序,也被稱為Swing應(yīng)用程序。它的優(yōu)點(diǎn)是Java的優(yōu)點(diǎn):“Write onceRun anywhere”;它的缺點(diǎn)也是Java的缺點(diǎn):“性能問題要命”。

    4.1 Swing單線程模型

    桌面應(yīng)用程序生命周期可以概括如下:

     

    STEP 1:初始化界面;

    STEP 2:等待你的event,主要還是鼠標(biāo)和鍵盤event

    STEP 3event一到,執(zhí)行相應(yīng)的業(yè)務(wù)邏輯代碼;

    STEP 4:根據(jù)結(jié)果,刷新界面,用戶看到;

    STEP 5:然后,又到步驟2,直到你退出。

     

    所謂Swing單線程模型的意思就是,所有和“界面”有關(guān)系的代碼都在Swing規(guī)定的線程(稱為Swing線程)里按照順序被執(zhí)行,不可以用自己定義的線程跟“界面”有任何的接觸(例外就不贅述了)。這里的“界面”指的是Jcomponent的子類,容器、按鈕、畫布都屬于界面的范圍。這里的“和界面有關(guān)系”包括event響應(yīng)、repaint、改變屬性等等。

     

    簡單來說,就是不能用自己的線程控制這些Jcomponent對(duì)象啦。

     

    真衰,這么干的原因還不是讓Java的桌面程序不至于太慢,結(jié)果所有(也有例外)Swing的類都被設(shè)計(jì)成“非”threadsafe的,因此也只能讓一個(gè)線程(Swing線程)訪問了。

    4.2 Long-Running Event Callbacks

    Swing編程中最大的一個(gè)麻煩就是處理“長時(shí)間事件響應(yīng)”。對(duì)照上面生命周期的step3event一到,執(zhí)行相應(yīng)的業(yè)務(wù)邏輯代碼),“長時(shí)間事件響應(yīng)”的意思就是Step3執(zhí)行的時(shí)間太長了,方法長期返回不了,以至把整個(gè)Swing線程的生命周期阻塞了,用戶看起來就像死機(jī)了。

     

    而一般這種情況,這個(gè)“長時(shí)間事件響應(yīng)”都是在Swing線程中執(zhí)行的,因此阻塞了才會(huì)這么大件事。

     

    那就把它移出Swing線程吧,讓它自己到另外的線程里面去做。這樣即使你阻塞了,也不至于阻塞Swing線程這個(gè)事關(guān)給用戶感覺的線程。

     

    但問題還沒有完,盡管上面的step3,也就是這個(gè)“長時(shí)間事件響應(yīng)”的確對(duì)Swing線程沒有影響了,Swing線程不會(huì)被阻塞了。但是在新線程(稱為N進(jìn)程)里,程序到了step4(根據(jù)結(jié)果,刷新界面,用戶看到), 它要根據(jù)step3的結(jié)果去刷新界面,把結(jié)果顯示給用戶。而根據(jù)Swing的單線程模型,N進(jìn)程是沒有權(quán)利去接觸界面對(duì)象的,只有Swing線程才有這個(gè)權(quán)利。所以,身處N進(jìn)程的step4又必須被放回到Swing線程里去執(zhí)行。

     

    這樣,來來回回,麻麻煩煩,把我Swing暈了,怪不得叫Swing,真是“忽悠”的意思啊。這里得到靈感,以后都用忽悠來翻譯Swing,呵呵。

    5 Swing Thread Programming

    為了把一些跟界面相關(guān)的代碼放回到Swing線程里去執(zhí)行,Swing類庫中提供了方法,我懶得說了。

     

    //把任務(wù)仍回給Swing執(zhí)行,不阻塞本線程

    invokeLater(Runnable GUITask)

     

    //把任務(wù)仍回給Swing執(zhí)行,阻塞本線程

    invokeAndWait(Runnable GUITask)

     

    當(dāng)然,除了直接用這兩個(gè)方法處理長時(shí)間事件響應(yīng)外,這幾天在網(wǎng)上還看到了另外兩個(gè)方法。

    5.1 SwingWorker

    提供了一個(gè)幫助類SwingWorker,使用方便。它把這些來來回回,麻麻煩煩的線程邏輯封裝起來。簡化使用Swing多線程的復(fù)雜度。

     

    詳細(xì)了解,請(qǐng)點(diǎn)擊相關(guān)頁面。不好訪問,也可以本站下載pdf版本

    5.2 Event-Dispatch方法

    使用觀察者模式重構(gòu)系統(tǒng),優(yōu)化Swing多線程程序的設(shè)計(jì)。方法基本近似上文的“設(shè)計(jì)并行程序的好辦法”。它和SwingWork最大的區(qū)別就是,使用它是要重新設(shè)計(jì)系統(tǒng)的,會(huì)產(chǎn)生基于“觀察者模式”的角色類的。

     

    詳細(xì)了解,請(qǐng)點(diǎn)擊相關(guān)頁面。不好訪問,也可以本站下載pdf版本

    6 結(jié)論

    想借Swing Thread Programming探討一下多線程設(shè)計(jì)的一些初級(jí)問題,并推薦了一下“觀察者模式”。

     

    posted on 2006-03-14 01:51 marco 閱讀(2603) 評(píng)論(2)  編輯  收藏 所屬分類: -=Design Pattern=--=Java Techs=-

    Feedback

    # re: Swing聯(lián)想雜憶 2006-04-15 19:22 FIONA
    ms很復(fù)雜,耐著性子看下去了。。。發(fā)現(xiàn)確實(shí)很復(fù)雜。
    發(fā)現(xiàn)你ms憤青,卻比較現(xiàn)實(shí)實(shí)干,哈  回復(fù)  更多評(píng)論
      

    # re: Swing聯(lián)想雜憶 2007-05-30 17:37 郭人瑋
    世界永遠(yuǎn)都是并行的 或者 它的頻率跑的特別快的  回復(fù)  更多評(píng)論
      

    主站蜘蛛池模板: 亚洲国产精品热久久| 国产精品无码一二区免费| rh男男车车的车车免费网站| 日本一区二区三区在线视频观看免费| 无人视频在线观看免费播放影院| 成人毛片免费播放| 国产免费观看视频| 亚洲AV中文无码乱人伦下载| 亚洲香蕉久久一区二区| 亚洲高清一区二区三区电影| 久久久久久久久久免免费精品| 99久久综合精品免费| 最近2019中文字幕mv免费看| 亚洲熟妇无码八V在线播放| 亚欧乱色国产精品免费视频| 亚洲精品麻豆av| 国产成人精品日本亚洲网址 | 国产AV无码专区亚洲A∨毛片| 亚洲伊人久久大香线焦| 老司机福利在线免费观看| 3344永久在线观看视频免费首页| 国产成人在线免费观看| 免费毛片毛片网址| 国产成人亚洲综合色影视| 99久久免费精品高清特色大片| 亚洲精品欧洲精品| 怡红院免费的全部视频| 日韩一区二区三区免费体验| 久久精品国产亚洲av日韩 | 两个人看的www免费| 亚洲综合色一区二区三区小说| 青青青免费国产在线视频小草| 久久久久噜噜噜亚洲熟女综合 | 最近免费中文字幕大全视频 | 亚洲综合另类小说色区色噜噜| 日本亚洲色大成网站www久久| 国产精品区免费视频| 亚洲第一视频在线观看免费| 亚洲AV综合色区无码二区偷拍| 国产自国产自愉自愉免费24区| 亚洲黄色免费网站|