天天看點

黑馬程式員-面試題(一)-交通燈管理系統引用

一、交通燈管理系統

模拟實作十字路口的交通燈管理系統邏輯,具體需求如下:

異步随機生成按照各個路線行駛的車輛。

   例如:

       由南向而來去往北向的車輛 ---- 直行車輛

       由西向而來去往南向的車輛 ---- 右轉車輛

       由東向而來去往南向的車輛 ---- 左轉車輛

       。。。

信号燈忽略黃燈,隻考慮紅燈和綠燈。

應考慮左轉車輛控制信号燈,右轉車輛不受信号燈控制。

具體信号燈控制邏輯與現實生活中普通交通燈控制邏輯相同,不考慮特殊情況下的控制邏輯。

  注:南北向車輛與東西向車輛交替放行,同方向等待車輛應先放行直行車輛而後放行左轉車輛。

每輛車通過路口時間為1秒(提示:可通過線程Sleep的方式模拟)。

随機生成車輛時間間隔以及紅綠燈交換時間間隔自定,可以設定。

不要求實作GUI,隻考慮系統邏輯實作,可通過Log方式展現程式運作結果。

二、需求分析:

  模拟一個十字路口:

                  

黑馬程式員-面試題(一)-交通燈管理系統引用

  總共有12條路線:S2N,S2W,S2E,E2W,E2S,E2N,N2S,N2E,N2W,W2E,W2N,W2S。假設每條路線都有一個紅綠燈對其控制,那麼通過需求可以知道右轉彎的4條路線:S2E,E2N,N2W,W2S的控制燈可以假設稱為常綠狀态。又因為其他的8條路線是亮亮對應的,則可以歸為4組,是以,程式隻需考慮圖上标注了數字的4條路線的控制燈的切換順序。

  注意:這裡的“2”,相當于“to” 。

三、面向對象的分析與設計

 1、類的分析:

  面向對象設計把握一個重要的經驗:誰擁有資料,誰就對外提供操作這些資料的方法。例如:

  1、“兩塊石頭磨成了一把石刀,石刀可以砍樹,砍成木頭,木頭做成椅子”

  2、“球從一根繩子的一段移動到另一端”分析其有多少個對象。

  對于第1題,我們可以簡單的想到有幾個對象:Stone, Stone Knife , Tree ,Wood ,Chair ,那麼石頭變成石刀、樹砍成木頭以及木頭做成椅子是誰的方法呢?因為誰擁有資料,誰就對外提供操作這些資料的方法,是以 Stone Knife =  StoneFactory.makeStoneKnife(Stone) ,Wood = TreeFactory.makeWood(Tree) , Chair = WoodFactory.makeChair(Wood) ,是以他們之間的聯系和對應的對象都一清二楚了。

  那麼對于交通燈管理系統中,有多少個對象呢?

  初步假設:紅綠燈、紅綠燈控制系統、汽車、路線。在汽車要通過路口時的條件是:汽車行駛的路線上對應的紅綠燈為綠色。根據需求得到,不需要提現車移動的過程,而是提現哪條路上的車可以走,即捕捉路上減少一輛車的過程,則可以知道汽車可以用設定為一個具體的對象。但是路線中必定也存儲着車輛的集合,而且路線對象上就應該有增加和減少車輛的方法。是以,我們隻需建立紅綠燈、紅綠燈控制系統、路線,三種類。

 2、類的功能分析:

  > 每條路線上都會出現多輛車,路線上要随機增加新的車,在燈綠期間還要每秒鐘減少一輛車。

    設計一個Road類來表示路線,每個Road對象代表一條路線,總共有12條路線,即系統中總共要産生12個Road執行個體對象。

    

    每條路線上随機增加新的車輛,增加到一個集合中儲存。

    每條路線每隔一秒都會檢查控制本路線的燈是否為綠,是則将本路線儲存車的集合中的第一輛車移除,即表示車穿過了路口。

   

  > 每條路線每隔一秒都會檢查控制本路線的燈是否為綠,一個燈由綠變紅時,應該将下一個方向的燈變綠。

    設計一個Lamp類來表示一個交通燈,每個交通燈都維護一個狀态:亮(綠)或不亮(紅),每個交通燈要有變亮和變黑的方法,并且能傳回自己的亮黑狀态。

    總共有12條路線,是以,系統中總共要産生12個交通燈。右拐彎的路線本來不受燈的控制,但是為了讓程式采用統一的處理方式,故假設出有四個右拐彎的燈,隻是這些燈為常亮狀态,即永遠不變黑。

    除了右拐彎方向的其他8條路線的燈,它們是兩兩成對的,可以歸為4組,是以,在程式設計處理時,隻要從這4組中各取出一個燈,對這4個燈依次輪詢變亮,與這4個燈方向對應的燈則随之一同變化,是以Lamp類中要有一個變量來記住自己相反方向的燈,在一個Lamp對象的變亮和變黑方法中,将對應方向的燈也變亮和變黑。每個燈變黑時,都伴随者下一個燈的變亮,Lamp類中還用一個變量來記住自己的下一個燈。

    無論在程式的什麼地方去獲得某個方向的燈時,每次獲得的都是同一個執行個體對象,是以Lamp類改用枚舉來做顯然具有很大的友善性,永遠都隻有代表12個方向的燈的執行個體對象。

    設計一個LampController類,它定時讓目前的綠燈變紅。

四、編寫:

  Road 類的編寫:

  1、每個Road對象都有一個name成員變量來代表方向,有一個vehicles成員變量來代表方向上的車輛集合。

  

  2、在Road對象的構造方法中啟動一個線程每隔一個随機的時間向vehicles集合中增加一輛車(用一個“路線名_id”形式的字元串進行表示)。

  3、在Road對象的構造方法中啟動一個定時器,每隔一秒檢查該方向上的燈是否為綠,是則列印車輛集合和将集合中的第一輛車移除掉。

黑馬程式員-面試題(一)-交通燈管理系統引用
黑馬程式員-面試題(一)-交通燈管理系統引用

   

  Lamp 類的編寫:

  1、系統中有12個方向上的燈,在程式的其他地方要根據燈的名稱就可以獲得對應的燈的執行個體對象,綜合這些因素,将Lamp類用java5中的枚舉形式定義更為簡單。

  2、每個Lamp對象中的亮黑狀态用lighted變量表示,選用S2N、S2W、E2W、E2N這四個方向上的Lamp對象依次輪詢變亮,Lamp對象中還要有一個oppositeLampName變量來表示它們相反方向的燈,再用一個nextLampName變量來表示此燈變亮後的下一個變亮的燈。這三個變量用構造方法的形式進行指派,因為枚舉元素必須在定義之後引用,是以無法再構造方法中彼此互相引用,是以,相反方向和下一個方向的燈用字元串形式表示。

  3、增加讓Lamp變亮和變黑的方法:light和blackOut,對于S2N、S2W、E2W、E2N這四個方向上的Lamp對象,這兩個方法内部要讓相反方向的燈随之變亮和變黑,blackOut方法還要讓下一個燈變亮。

  4、除了S2N、S2W、E2W、E2N這四個方向上的Lamp對象之外,其他方向上的Lamp對象的nextLampName和oppositeLampName屬性設定為null即可,并且S2N、S2W、E2W、E2N這四個方向上的Lamp對象的nextLampName和oppositeLampName屬性必須設定為null,以便防止light和blackOut進入死循環。

黑馬程式員-面試題(一)-交通燈管理系統引用
黑馬程式員-面試題(一)-交通燈管理系統引用

   LampController 類的編寫

   1、整個系統中隻能有一套交通燈控制系統,是以,LampController類最好是設計成單例。

   2、LampController構造方法中要設定第一個為綠的燈。

   3、LampController對象的start方法中将目前燈變綠,然後啟動一個定時器,每隔10秒将目前燈變紅和将下一個燈變綠。

黑馬程式員-面試題(一)-交通燈管理系統引用
黑馬程式員-面試題(一)-交通燈管理系統引用

   MainClass 類的編寫

  1、用for循環建立出代表12條路線的對象。

  2、接着再獲得LampController對象并調用其start方法。

黑馬程式員-面試題(一)-交通燈管理系統引用
黑馬程式員-面試題(一)-交通燈管理系統引用

   運作結果:

黑馬程式員-面試題(一)-交通燈管理系統引用
黑馬程式員-面試題(一)-交通燈管理系統引用

  總結:通過交通管理系統,最深刻的便是面向對象設計的學習:誰擁有資料,誰就對外提供操作這些資料的方法。

若轉載請注明出處!若有疑問,請回複交流!

繼續閱讀