少年阿賓

          那些青春的歲月

            BlogJava :: 首頁(yè) :: 聯(lián)系 :: 聚合  :: 管理
            500 Posts :: 0 Stories :: 135 Comments :: 0 Trackbacks

          #

          JAR上傳到NEXUS
          mvn deploy:deploy-file -DgroupId=org.csource.fastdfs -DartifactId=fastdfs-client -Dversion=1.24 -Dpackaging=jar -Dfile=D:\\fastdfs-client-1.24.jar -Durl=http://172.16.6.214:8081/nexus/content/groups/public/ -DrepositoryId=nexus
          JAR創(chuàng)建到本地
          mvn install:install-file -DgroupId=com.home.link -DartifactId=fastdfs-client -Dversion=1.24 -Dpackaging=jar -Dfile=D:\\fastdfs-client-1.24.jar










          posted @ 2015-05-06 17:40 abin 閱讀(1235) | 評(píng)論 (0)編輯 收藏

          RAID 是“獨(dú)立磁盤冗余陣列”(最初為“廉價(jià)磁盤冗余陣列”)的縮略語(yǔ),1987 年由Patterson Gibson Katz 在加州大學(xué)伯克利分院的一篇文章中定義。RAID 陣列技術(shù)允許將一系列磁盤分組,以實(shí)現(xiàn)提高可用性的目的,并提供為實(shí)現(xiàn)數(shù)據(jù)保護(hù)而必需的數(shù)據(jù)冗余,有時(shí)還有改善性能的作用。我們將對(duì)七個(gè)RAID 級(jí)別: 01351030 50 作些說(shuō)明。最前面的個(gè)級(jí)別0135,)已被定為工業(yè)標(biāo)準(zhǔn),10 級(jí)、30 級(jí)和50 級(jí)則反應(yīng)了ACCSTOR2000 磁盤陣列可以提供的功能。了解每個(gè)級(jí)別的特征將有助于您判斷哪個(gè)級(jí)別最適合您的需要,本文的最后一部分將提供一份指導(dǎo)方針,幫助您選擇最適合您需要的RAID 級(jí)別。RAID 級(jí)別可以通過軟件或硬件實(shí)現(xiàn)。許多但不是全部網(wǎng)絡(luò)操作系統(tǒng)支持的RAID 級(jí)別至少要達(dá)到級(jí),RAID103050 ACCSTOR2000 磁盤陣列控制下才能實(shí)現(xiàn)。基于軟件的RAID 需要使用主機(jī)CPU 周期和系統(tǒng)內(nèi)存,從而增加了系統(tǒng)開銷,直接影響系統(tǒng)的性能。磁盤陣列控制器把RAID 的計(jì)算和操縱工作由軟件移到了專門的硬件上,一般比軟件實(shí)現(xiàn)RAID 的系統(tǒng)性能要好。
           


           


          RAID 0
          1
          、RAID 0又稱為Stripe(條帶化)或Striping,它代表了所有RAID級(jí)別中最高的存儲(chǔ)性能。RAID 0提高存儲(chǔ)性能的原理是把連續(xù)的數(shù)據(jù)分散到多個(gè)磁盤上存取,這樣,系統(tǒng)有數(shù)據(jù)請(qǐng)求就可以被多個(gè)磁盤并行的執(zhí)行,每個(gè)磁盤執(zhí)行屬于它自己的那部分?jǐn)?shù)據(jù)請(qǐng)求。這種數(shù)據(jù)上的并行操作可以充分利用總線的帶寬,顯著提高磁盤整體存取性能。
          2、系統(tǒng)向三個(gè)磁盤組成的邏輯硬盤(RADI 0 磁盤組)發(fā)出的I/O數(shù)據(jù)請(qǐng)求被轉(zhuǎn)化為3項(xiàng)操作,其中的每一項(xiàng)操作都對(duì)應(yīng)于一塊物理硬盤。我們從圖中可以清楚的看到通過建立RAID 0,原先順序的數(shù)據(jù)請(qǐng)求被分散到所有的三塊硬盤中同時(shí)執(zhí)行。從理論上講,三塊硬盤的并行操作使同一時(shí)間內(nèi)磁盤讀寫速度提升了3倍。 但由于總線帶寬等多種因素的影響,實(shí)際的提升速率肯定會(huì)低于理論值,但是,大量數(shù)據(jù)并行傳輸與串行傳輸比較,提速效果顯著顯然毋庸置疑。
          3、RAID 0的缺點(diǎn)是不提供數(shù)據(jù)冗余,因此一旦用戶數(shù)據(jù)損壞,損壞的數(shù)據(jù)將無(wú)法得到恢復(fù)。
          4、RAID 0具有的特點(diǎn),使其特別適用于對(duì)性能要求較高,而對(duì)數(shù)據(jù)安全不太在乎的領(lǐng)域,如圖形工作站等。對(duì)于個(gè)人用戶,RAID 0也是提高硬盤存儲(chǔ)性能的絕佳選擇。

          RAID 1
          1、RAID 1又稱為Mirror或Mirroring(鏡像),它的宗旨是最大限度的保證用戶數(shù)據(jù)的可用性和可修復(fù)性。
           RAID 1的操作方式是把用戶寫入硬盤的數(shù)據(jù)百分之百地自動(dòng)復(fù)制到另外一個(gè)硬盤上。
          2、當(dāng)讀取數(shù)據(jù)時(shí),系統(tǒng)先從RAID 0的源盤讀取數(shù)據(jù),如果讀取數(shù)據(jù)成功,則系統(tǒng)不去管備份盤上的數(shù)據(jù);如果讀取源盤數(shù)據(jù)失敗,則系統(tǒng)自動(dòng)轉(zhuǎn)而讀取備份盤上的數(shù)據(jù),不會(huì)造成用戶工作任務(wù)的中斷。當(dāng)然,我們應(yīng)當(dāng)及時(shí)地更換損壞的硬盤并利用備份數(shù)據(jù)重新建立Mirror,避免備份盤在發(fā)生損壞時(shí),造成不可挽回的數(shù)據(jù)損失。
          3、由于對(duì)存儲(chǔ)的數(shù)據(jù)進(jìn)行百分之百的備份,在所有RAID級(jí)別中,RAID 1提供最高的數(shù)據(jù)安全保障。同樣,由于數(shù)據(jù)的百分之百備份,備份數(shù)據(jù)占了總存儲(chǔ)空間的一半,因而Mirror(鏡像)的磁盤空間利用率低,存儲(chǔ)成本高。
          4、Mirror雖不能提高存儲(chǔ)性能,但由于其具有的高數(shù)據(jù)安全性,使其尤其適用于存放重要數(shù)據(jù),如服務(wù)器和數(shù)據(jù)庫(kù)存儲(chǔ)等領(lǐng)域。

          RAID 10=RAID 0+1
          1、正如其名字一樣RAID 0+1是RAID 0和RAID 1的組合形式,也稱為RAID 10。
          2、以四個(gè)磁盤組成的RAID 0+1為例,其數(shù)據(jù)存儲(chǔ)方式如圖所示:RAID 0+1是存儲(chǔ)性能和數(shù)據(jù)安全兼顧的方案。它在提供與RAID 1一樣的數(shù)據(jù)安全保障的同時(shí),也提供了與RAID 0近似的存儲(chǔ)性能。
          3、由于RAID 0+1也通過數(shù)據(jù)的100%備份功能提供數(shù)據(jù)安全保障,因此RAID 0+1的磁盤空間利用率與RAID 1相同,存儲(chǔ)成本高。
          4、RAID 0+1的特點(diǎn)使其特別適用于既有大量數(shù)據(jù)需要存取,同時(shí)又對(duì)數(shù)據(jù)安全性要求嚴(yán)格的領(lǐng)域,如銀行、金融、商業(yè)超市、倉(cāng)儲(chǔ)庫(kù)房、各種檔案管理等。

          RAID 5
          1、RAID 5 是一種存儲(chǔ)性能、數(shù)據(jù)安全和存儲(chǔ)成本兼顧的存儲(chǔ)解決方案。 以四個(gè)硬盤組成的RAID 5為例,其數(shù)據(jù)存儲(chǔ)方式如圖4所示:圖中,P0為D0,D1和D2的奇偶校驗(yàn)信息,其它以此類推。由圖中可以看出,RAID 5不對(duì)存儲(chǔ)的數(shù)據(jù)進(jìn)行備份,而是把數(shù)據(jù)和相對(duì)應(yīng)的奇偶校驗(yàn)信息存儲(chǔ)到組成RAID5的各個(gè)磁盤上,并且奇偶校驗(yàn)信息和相對(duì)應(yīng)的數(shù)據(jù)分別存儲(chǔ)于不同的磁盤上。當(dāng)RAID5的一個(gè)磁盤數(shù)據(jù)發(fā)生損壞后,利用剩下的數(shù)據(jù)和相應(yīng)的奇偶校驗(yàn)信息去恢復(fù)被損壞的數(shù)據(jù)。
          2、RAID 5可以理解為是RAID 0和RAID 1的折衷方案。RAID 5可以為系統(tǒng)提供數(shù)據(jù)安全保障,但保障程度要比Mirror低而磁盤空間利用率要比Mirror高。RAID 5具有和RAID 0相近似的數(shù)據(jù)讀取速度,只是多了一個(gè)奇偶校驗(yàn)信息,寫入數(shù)據(jù)的速度比對(duì)單個(gè)磁盤進(jìn)行寫入操作稍慢。同時(shí)由于多個(gè)數(shù)據(jù)對(duì)應(yīng)一個(gè)奇偶校驗(yàn)信息,RAID 5的磁盤空間利用率要比RAID 1高,存儲(chǔ)成本相對(duì)較低。

           



          posted @ 2015-05-03 18:23 abin 閱讀(317) | 評(píng)論 (0)編輯 收藏

           JDK中的實(shí)現(xiàn)
          在JDK中LinkedHashMap可以作為L(zhǎng)RU算法以及插入順序的實(shí)現(xiàn),LinkedHashMap繼承自HashMap,底層結(jié)合hash表和雙向鏈表,元素的插入和查詢等操作通過計(jì)算hash值找到其數(shù)組位置,在做插入或則查詢操作是,將元素插入到鏈表的表頭(當(dāng)然得先刪除鏈表中的老元素),如果容量滿了,則刪除LRU這個(gè)元素,在鏈表表尾的元素即是。
          LinkedHashMap的時(shí)間復(fù)雜度和HashMap差不多,雙向鏈表的刪除和表頭插入等操作都是O(1)復(fù)雜度,故不會(huì)影響HashMap的操作性能,插入,查詢,刪除LRU元素等操作均是O(1)的時(shí)間復(fù)雜度。
          LinkedHashMap不是線程安全的類,用于多線程緩存則需要花點(diǎn)心思去同步它了,JDK中有支持并發(fā)的高性能ConcurrenHashMap,沒有ConcurrenListHashMap的實(shí)現(xiàn),故要使用支持并發(fā)的高性能LRU算法還得靠自己去繼承ConcurrenHashMap或則其他方式實(shí)現(xiàn)。Google以及其它資深研發(fā)團(tuán)隊(duì)已有ConcurrenListHashMap的實(shí)現(xiàn)
          當(dāng)然知道了原理,我們自己也可以來(lái)實(shí)現(xiàn)LRU算法
          1.簡(jiǎn)單的計(jì)數(shù)或則LU時(shí)間標(biāo)記法
          底層使用hash表,插入和訪問的時(shí)間都可以做到O(1)復(fù)雜度,容量滿了需要?jiǎng)h除LRU,則需要遍歷一遍數(shù)組,通過計(jì)數(shù)或則LU時(shí)間得到LRU,刪除之,時(shí)間復(fù)雜度O(n)。此算法簡(jiǎn)單容易實(shí)現(xiàn),適合數(shù)據(jù)量不大的需求
          2.通過棧或雙向鏈表
          這種算法通過維護(hù)元素的在鏈表中的順序來(lái)達(dá)到計(jì)算元素的訪問熱度,不需要額外的空間來(lái)計(jì)數(shù)或則記錄訪問時(shí)間。
          插入時(shí),先檢查改元素存在此鏈表中沒有,有的刪除之,然后再將元素插入表頭。
          訪問時(shí),遍歷數(shù)組查找該元素,然后將該元素移動(dòng)至表頭。
          這樣一來(lái),最近被訪問的元素都在表頭,故要找出LRU則只需要?jiǎng)h除表尾元素即可。插入和訪問的時(shí)間復(fù)雜度均為O(n),如果用來(lái)作為緩存(查詢操作頻繁),相比hash表的實(shí)現(xiàn),性能相當(dāng)不好啊
          3.結(jié)合HashMap和雙向鏈表
          通過上面可知道HashMap可實(shí)現(xiàn)讀寫O(1)復(fù)雜度,但是找出LRU需要遍歷整個(gè)數(shù)組,而通過維護(hù)鏈表則相反,僅需要O(1)就可以找出LRU,故將兩者結(jié)合起來(lái),實(shí)現(xiàn)綜合復(fù)雜度為O(1)的LRU算法
          使用數(shù)組來(lái)存放元素,插入時(shí)通過hash計(jì)算出其位置,然后改變?cè)撛卦阪湵碇械闹羔槪瑑蓚€(gè)操作的時(shí)間復(fù)雜度均為1。具體實(shí)現(xiàn)可參考JDK的LinkedHashMap
           
           
          http://www.360doc.com/content/14/0402/09/10504424_365635496.shtml
          posted @ 2015-04-24 00:41 abin 閱讀(680) | 評(píng)論 (1)編輯 收藏

          Zookeeper的核心是原子廣播,這個(gè)機(jī)制保證了各個(gè)Server之間的同步。實(shí)現(xiàn)這個(gè)機(jī)制的協(xié)議叫做Zab協(xié)議。Zab協(xié)議有兩種模式,它們分別是恢復(fù)模式(選主)和廣播模式(同步)。當(dāng)服務(wù)啟動(dòng)或者在領(lǐng)導(dǎo)者崩潰后,Zab就進(jìn)入了恢復(fù)模式,當(dāng)領(lǐng)導(dǎo)者被選舉出來(lái),且大多數(shù)Server完成了和leader的狀態(tài)同步以后,恢復(fù)模式就結(jié)束了。狀態(tài)同步保證了leader和Server具有相同的系統(tǒng)狀態(tài)。
          為了保證事務(wù)的順序一致性,zookeeper采用了遞增的事務(wù)id號(hào)(zxid)來(lái)標(biāo)識(shí)事務(wù)。所有的提議(proposal)都在被提出的時(shí)候加上了zxid。實(shí)現(xiàn)中zxid是一個(gè)64位的數(shù)字,它高32位是epoch用來(lái)標(biāo)識(shí)leader關(guān)系是否改變,每次一個(gè)leader被選出來(lái),它都會(huì)有一個(gè)新的epoch,標(biāo)識(shí)當(dāng)前屬于那個(gè)leader的統(tǒng)治時(shí)期。低32位用于遞增計(jì)數(shù)。
          每個(gè)Server在工作過程中有三種狀態(tài):
          LOOKING:當(dāng)前Server不知道leader是誰(shuí),正在搜尋
          LEADING:當(dāng)前Server即為選舉出來(lái)的leader
          FOLLOWING:leader已經(jīng)選舉出來(lái),當(dāng)前Server與之同步
           
          Leader選舉流程: 
          當(dāng)leader崩潰或者leader失去大多數(shù)的follower,這時(shí)候zk進(jìn)入恢復(fù)模式,恢復(fù)模式需要重新選舉出一個(gè)新的leader,讓所有的Server都恢復(fù)到一個(gè)正確的狀態(tài)。Zk的選舉算法有兩種:一種是基于basic paxos實(shí)現(xiàn)的,另外一種是基于fast paxos算法實(shí)現(xiàn)的。系統(tǒng)默認(rèn)的選舉算法為fast paxos。先介紹basic paxos流程:
          1 .選舉線程由當(dāng)前Server發(fā)起選舉的線程擔(dān)任,其主要功能是對(duì)投票結(jié)果進(jìn)行統(tǒng)計(jì),并選出推薦的Server;
          2 .選舉線程首先向所有Server發(fā)起一次詢問(包括自己);
          3 .選舉線程收到回復(fù)后,驗(yàn)證是否是自己發(fā)起的詢問(驗(yàn)證zxid是否一致),然后獲取對(duì)方的id(myid),并存儲(chǔ)到當(dāng)前詢問對(duì)象列表中,最后獲取對(duì)方提議的leader相關(guān)信息( id,zxid),并將這些信息存儲(chǔ)到當(dāng)次選舉的投票記錄表中;
          4. 收到所有Server回復(fù)以后,就計(jì)算出zxid最大的那個(gè)Server,并將這個(gè)Server相關(guān)信息設(shè)置成下一次要投票的Server;
          5. 線程將當(dāng)前zxid最大的Server設(shè)置為當(dāng)前Server要推薦的Leader,如果此時(shí)獲勝的Server獲得n/2 + 1的Server票數(shù), 設(shè)置當(dāng)前推薦的leader為獲勝的Server,將根據(jù)獲勝的Server相關(guān)信息設(shè)置自己的狀態(tài),否則,繼續(xù)這個(gè)過程,直到leader被選舉出來(lái)。
          通過流程分析我們可以得出:要使Leader獲得多數(shù)Server的支持,則Server總數(shù)必須是奇數(shù)2n+1,且存活的Server的數(shù)目不得少于n+1.
          每個(gè)Server啟動(dòng)后都會(huì)重復(fù)以上流程。在恢復(fù)模式下,如果是剛從崩潰狀態(tài)恢復(fù)的或者剛啟動(dòng)的server還會(huì)從磁盤快照中恢復(fù)數(shù)據(jù)和會(huì)話信息,zk會(huì)記錄事務(wù)日志并定期進(jìn)行快照,方便在恢復(fù)時(shí)進(jìn)行狀態(tài)恢復(fù)。



          fast paxos流程是在選舉過程中,某Server首先向所有Server提議自己要成為leader,當(dāng)其它Server收到提議以后,解決epoch和zxid的沖突,并接受對(duì)方的提議,然后向?qū)Ψ桨l(fā)送接受提議完成的消息,重復(fù)這個(gè)流程,最后一定能選舉出Leader。


          zookeeper數(shù)據(jù)同步過程: 
          選完leader以后,zk就進(jìn)入狀態(tài)同步過程。
          1. leader等待server連接;
          2 .Follower連接leader,將最大的zxid發(fā)送給leader;
          3 .Leader根據(jù)follower的zxid確定同步點(diǎn);
          4 .完成同步后通知follower 已經(jīng)成為uptodate狀態(tài);
          5 .Follower收到uptodate消息后,又可以重新接受client的請(qǐng)求進(jìn)行服務(wù)了。



          工作流程 
          Leader工作流程 
          Leader主要有三個(gè)功能:
          1 .恢復(fù)數(shù)據(jù);
          2 .維持與Learner的心跳,接收Learner請(qǐng)求并判斷Learner的請(qǐng)求消息類型;
          3 .Learner的消息類型主要有PING消息、REQUEST消息、ACK消息、REVALIDATE消息,根據(jù)不同的消息類型,進(jìn)行不同的處理。
          PING消息是指Learner的心跳信息;REQUEST消息是Follower發(fā)送的提議信息,包括寫請(qǐng)求及同步請(qǐng)求;ACK消息是Follower的對(duì)提議的回復(fù),超過半數(shù)的Follower通過,則commit該提議;REVALIDATE消息是用來(lái)延長(zhǎng)SESSION有效時(shí)間。Leader的工作流程簡(jiǎn)圖如下所示,在實(shí)際實(shí)現(xiàn)中,流程要比下圖復(fù)雜得多,啟動(dòng)了三個(gè)線程來(lái)實(shí)現(xiàn)功能。



          2.3.2 Follower工作流程 
          Follower主要有四個(gè)功能:
          1. 向Leader發(fā)送請(qǐng)求(PING消息、REQUEST消息、ACK消息、REVALIDATE消息);
          2 .接收Leader消息并進(jìn)行處理;
          3 .接收Client的請(qǐng)求,如果為寫請(qǐng)求,發(fā)送給Leader進(jìn)行投票;
          4 .返回Client結(jié)果。
          Follower的消息循環(huán)處理如下幾種來(lái)自Leader的消息:
          1 .PING消息:心跳消息;
          2 .PROPOSAL消息:Leader發(fā)起的提案,要求Follower投票;
          3 .COMMIT消息:服務(wù)器端最新一次提案的信息;
          4 .UPTODATE消息:表明同步完成;
          5 .REVALIDATE消息:根據(jù)Leader的REVALIDATE結(jié)果,關(guān)閉待revalidate的session還是允許其接受消息;
          6 .SYNC消息:返回SYNC結(jié)果到客戶端,這個(gè)消息最初由客戶端發(fā)起,用來(lái)強(qiáng)制得到最新的更新。
          Follower的工作流程簡(jiǎn)圖如下所示,在實(shí)際實(shí)現(xiàn)中,F(xiàn)ollower是通過5個(gè)線程來(lái)實(shí)現(xiàn)功能的。





          http://www.it165.net/admin/html/201405/2997.html
          posted @ 2015-04-22 01:05 abin 閱讀(327) | 評(píng)論 (0)編輯 收藏

          靜態(tài)代理
          靜態(tài)代理相對(duì)來(lái)說(shuō)比較簡(jiǎn)單,無(wú)非就是聚合+多態(tài):
          參考:設(shè)計(jì)模式筆記 – Proxy 代理模式 (Design Pattern)
          動(dòng)態(tài)代理
          我們知道,通過使用代理,可以在被代理的類的方法的前后添加一些處理方法,這樣就達(dá)到了類似AOP的效果。而JDK中提供的動(dòng)態(tài)代理,就是實(shí)現(xiàn)AOP的絕好底層技術(shù)。
          JDK動(dòng)態(tài)代理
          JDK動(dòng)態(tài)代理主要涉及到j(luò)ava.lang.reflect包中的兩個(gè)類:Proxy和InvocationHandler。InvocationHandler是一個(gè)接口,通過實(shí)現(xiàn)該接口定義橫切邏輯,并通過反射機(jī)制調(diào)用目標(biāo)類的代碼,動(dòng)態(tài)將橫切邏輯和業(yè)務(wù)邏輯編制在一起。
          Proxy利用InvocationHandler動(dòng)態(tài)創(chuàng)建一個(gè)符合某一接口的實(shí)例,生成目標(biāo)類的代理對(duì)象。
          例子:Java筆記 – 反射 動(dòng)態(tài)代理
          CGLib動(dòng)態(tài)代理
          還有一個(gè)叫CGLib的動(dòng)態(tài)代理,CGLib全稱為Code Generation Library,是一個(gè)強(qiáng)大的高性能,高質(zhì)量的代碼生成類庫(kù),可以在運(yùn)行期擴(kuò)展Java類與實(shí)現(xiàn)Java接口,CGLib封裝了asm,可以再運(yùn)行期動(dòng)態(tài)生成新的class。和JDK動(dòng)態(tài)代理相比較:JDK創(chuàng)建代理有一個(gè)限制,就是只能為接口創(chuàng)建代理實(shí)例,而對(duì)于沒有通過接口定義業(yè)務(wù)方法的類,則可以通過CGLib創(chuàng)建動(dòng)態(tài)代理。

          CGLib采用非常底層的字節(jié)碼技術(shù),可以為一個(gè)類創(chuàng)建子類,并在子類中采用方法攔截的技術(shù)攔截所有父類方法的調(diào)用,并順勢(shì)織入橫切邏輯。

          JDK動(dòng)態(tài)代理和CGLib的比較

          CGLib所創(chuàng)建的動(dòng)態(tài)代理對(duì)象的性能比JDK所創(chuàng)建的代理對(duì)象性能高不少,大概10倍,但CGLib在創(chuàng)建代理對(duì)象時(shí)所花費(fèi)的時(shí)間卻比JDK動(dòng)態(tài)代理多大概8倍,所以對(duì)于singleton的代理對(duì)象或者具有實(shí)例池的代理,因?yàn)闊o(wú)需頻繁的創(chuàng)建新的實(shí)例,所以比較適合CGLib動(dòng)態(tài)代理技術(shù),反之則適用于JDK動(dòng)態(tài)代理技術(shù)。另外,由于CGLib采用動(dòng)態(tài)創(chuàng)建子類的方式生成代理對(duì)象,所以不能對(duì)目標(biāo)類中的final,private等方法進(jìn)行處理。所以,大家需要根據(jù)實(shí)際的情況選擇使用什么樣的代理了。

          同樣的,Spring的AOP編程中相關(guān)的ProxyFactory代理工廠內(nèi)部就是使用JDK動(dòng)態(tài)代理或CGLib動(dòng)態(tài)代理的,通過動(dòng)態(tài)代理,將增強(qiáng)(advice)應(yīng)用到目標(biāo)類中。


          JDK動(dòng)態(tài)代理主要用到j(luò)ava.lang.reflect包中的兩個(gè)類:Proxy和InvocationHandler.
           
          InvocationHandler是一個(gè)接口,通過實(shí)現(xiàn)該接口定義橫切邏輯,并通過反射機(jī)制調(diào)用目標(biāo)類的代碼,動(dòng)態(tài)的將橫切邏輯和業(yè)務(wù)邏輯編織在一起。
           
          Proxy利用InvocationHandler動(dòng)態(tài)創(chuàng)建一個(gè)符合某一接口的實(shí)例,生成目標(biāo)類的代理對(duì)象。

          posted @ 2015-04-22 00:22 abin 閱讀(629) | 評(píng)論 (0)編輯 收藏

          Cookie攻擊:
              防止Cookie被抓包了之后攻擊: 
              就是驗(yàn)證的東西盡量多就行了,比如里面添加IP驗(yàn)證,添加一些MAC地址,添加有效期,添加
          posted @ 2015-04-21 23:52 abin 閱讀(274) | 評(píng)論 (0)編輯 收藏

          NIO通常采用Reactor模式,AIO通常采用Proactor模式。AIO簡(jiǎn)化了程序的編寫,stream的讀取和寫入都有OS來(lái)完成,不需 要像NIO那樣子遍歷Selector。Windows基于IOCP實(shí)現(xiàn)AIO,Linux只有eppoll模擬實(shí)現(xiàn)了AIO。
          Java7之前的JDK只支持NIO和BIO,從7開始支持AIO。
          你說(shuō)的IO應(yīng)該指BIO,這種模式需要阻塞線程,一個(gè)IO需要一個(gè)線程,NIO由一個(gè)thread來(lái)監(jiān)聽connect事件,另外多個(gè)thread來(lái)監(jiān)聽讀寫事件,帶來(lái)性能上很大提高。

          基于原生nio的socket通信時(shí)一種很好的解決方案,基于事件的通知模式使得多并發(fā)時(shí)不用維持高數(shù)量的線程,高并發(fā)的socket服務(wù)器的java實(shí)現(xiàn)成為現(xiàn)實(shí)。不過原生nio代碼十分復(fù)雜,無(wú)論編寫還是修改都是一件頭疼的事。“屏蔽底層的繁瑣工作,讓程序員將注意力集中于業(yè)務(wù)邏輯本身”,有需求就有生產(chǎn)力進(jìn)步,

























          posted @ 2015-04-21 23:48 abin 閱讀(308) | 評(píng)論 (0)編輯 收藏

          狀態(tài)模式(state pattern)和策略模式(strategy pattern)的實(shí)現(xiàn)方法非常類似,都是利用多態(tài)把一些操作分配到一組相關(guān)的簡(jiǎn)單的類中,因此很多人認(rèn)為這兩種模式實(shí)際上是相同的。然而
          •在現(xiàn)實(shí)世界中,策略(如促銷一種商品的策略)和狀態(tài)(如同一個(gè)按鈕來(lái)控制一個(gè)電梯的狀態(tài),又如手機(jī)界面中一個(gè)按鈕來(lái)控制手機(jī))是兩種完全不同的思想。當(dāng)我們對(duì)狀態(tài)和策略進(jìn)行建模時(shí),這種差異會(huì)導(dǎo)致完全不同的問題。例如,對(duì)狀態(tài)進(jìn)行建模時(shí),狀態(tài)遷移是一個(gè)核心內(nèi)容;然而,在選擇策略時(shí),遷移與此毫無(wú)關(guān)系。另外,策略模式允許一個(gè)客戶選擇或提供一種策略,而這種思想在狀態(tài)模式中完全沒有。 
          •一個(gè)策略是一個(gè)計(jì)劃或方案,通過執(zhí)行這個(gè)計(jì)劃或方案,我們可以在給定的輸入條件下達(dá)到一個(gè)特定的目標(biāo)。策略是一組方案,他們可以相互替換;選擇一個(gè)策略,獲得策略的輸出。策略模式用于隨不同外部環(huán)境采取不同行為的場(chǎng)合。我們可以參考微軟企業(yè)庫(kù)底層Object Builder的創(chuàng)建對(duì)象的strategy實(shí)現(xiàn)方式。 
          •而狀態(tài)模式不同,對(duì)一個(gè)狀態(tài)特別重要的對(duì)象,通過狀態(tài)機(jī)來(lái)建模一個(gè)對(duì)象的狀態(tài);狀態(tài)模式處理的核心問題是狀態(tài)的遷移,因?yàn)樵趯?duì)象存在很多狀態(tài)情況下,對(duì)各個(gè)business flow,各個(gè)狀態(tài)之間跳轉(zhuǎn)和遷移過程都是及其復(fù)雜的。例如一個(gè)工作流,審批一個(gè)文件,存在新建、提交、已修改、HR部門審批中、老板審批中、HR審批失敗、老板審批失敗等狀態(tài),涉及多個(gè)角色交互,涉及很多事件,這種情況下用狀態(tài)模式(狀態(tài)機(jī))來(lái)建模更加合適;把各個(gè)狀態(tài)和相應(yīng)的實(shí)現(xiàn)步驟封裝成一組簡(jiǎn)單的繼承自一個(gè)接口或抽象類的類,通過另外的一個(gè)Context來(lái)操作他們之間的自動(dòng)狀態(tài)變換,通過event來(lái)自動(dòng)實(shí)現(xiàn)各個(gè)狀態(tài)之間的跳轉(zhuǎn)。在整個(gè)生命周期中存在一個(gè)狀態(tài)的遷移曲線,這個(gè)遷移曲線對(duì)客戶是透明的。我們可以參考微軟最新的WWF 狀態(tài)機(jī)工作流實(shí)現(xiàn)思想。 
          •在狀態(tài)模式中,狀態(tài)的變遷是由對(duì)象的內(nèi)部條件決定,外界只需關(guān)心其接口,不必關(guān)心其狀態(tài)對(duì)象的創(chuàng)建和轉(zhuǎn)化;而策略模式里,采取何種策略由外部條件(C)決定。 
          posted @ 2015-04-21 02:43 abin 閱讀(374) | 評(píng)論 (0)編輯 收藏

          Spring什么時(shí)候?qū)嵗痓ean,首先要分2種情況 
            第一:如果你使用BeanFactory作為Spring Bean的工廠類,則所有的bean都是在第一次使用該Bean的時(shí)候?qū)嵗?nbsp;
            第二:如果你使用ApplicationContext作為Spring Bean的工廠類,則又分為以下幾種情況: 
                 (1):如果bean的scope是singleton的,并且lazy-init為false(默認(rèn)是false,所以可以不用設(shè)置),則ApplicationContext啟動(dòng)的時(shí)候就實(shí)例化該Bean,并且將實(shí)例化的Bean放在一個(gè)map結(jié)構(gòu)的緩存中,下次再使用該Bean的時(shí)候,直接從這個(gè)緩存中取 
                 (2):如果bean的scope是singleton的,并且lazy-init為true,則該Bean的實(shí)例化是在第一次使用該Bean的時(shí)候進(jìn)行實(shí)例化 
                 (3):如果bean的scope是prototype的,則該Bean的實(shí)例化是在第一次使用該Bean的時(shí)候進(jìn)行實(shí)例化 


          1、lazy init 在getBean時(shí)實(shí)例化 
          2、非lazy的單例bean 容器初始化時(shí)實(shí)例化 
          3、prototype等 getBean時(shí)實(shí)例化




          spring三種實(shí)例化bean的方式

          在spring中有三中實(shí)例化bean的方式:

          一、使用構(gòu)造器實(shí)例化;

          二、使用靜態(tài)工廠方法實(shí)例化;

          三、使用實(shí)例化工廠方法實(shí)例化。

           

          每種實(shí)例化所采用的配置是不一樣的:

          一、使用構(gòu)造器實(shí)例化;

          這種實(shí)例化的方式可能在我們平時(shí)的開發(fā)中用到的是最多的,因?yàn)樵趚ml文件中配置簡(jiǎn)單并且也不需要額外的工廠類來(lái)實(shí)現(xiàn)。

          <!--applicationContext.xml配置:-->

          <bean id="personService" class="cn.mytest.service.impl.PersonServiceBean"></bean>
           id是對(duì)象的名稱,class是要實(shí)例化的類,然后再通過正常的方式進(jìn)調(diào)用實(shí)例化的類即可,比如:
          public void instanceSpring(){
                          //加載spring配置文件
          ApplicationContext ac = new ClassPathXmlApplicationContext(
          new String[]{
          "/conf/applicationContext.xml"
          });
          //調(diào)用getBean方法取得被實(shí)例化的對(duì)象。
          PersonServiceBean psb = (PersonServiceBean) ac.getBean("personService");
          psb.save();
          }

          采用這種實(shí)例化方式要注意的是:要實(shí)例化的類中如果有構(gòu)造器的話,一定要有一個(gè)無(wú)參的構(gòu)造器。

           

          二、使用靜態(tài)工廠方法實(shí)例化;

          根據(jù)這個(gè)中實(shí)例化方法的名稱就可以知道要想通過這種方式進(jìn)行實(shí)例化就要具備兩個(gè)條件:(一)、要有工廠類及其工廠方法;(二)、工廠方法是靜態(tài)的。OK,知道這兩點(diǎn)就好辦了,首先創(chuàng)建工程類及其靜態(tài)方法:

          package cn.mytest.service.impl;
          /**
          *創(chuàng)建工廠類
          *
          */
          public class PersonServiceFactory {
              //創(chuàng)建靜態(tài)方法
          public static PersonServiceBean createPersonServiceBean(){
                   //返回實(shí)例化的類的對(duì)象
          return new PersonServiceBean();
          }
          }
          然后再去配置spring配置文件,配置的方法和上面有點(diǎn)不同,這里也是關(guān)鍵所在
          <!--applicationContext.xml配置:-->
          <bean id="personService1" class="cn.mytest.service.impl.PersonServiceFactory" factory-method="createPersonServiceBean"></bean>

           id是實(shí)例化的對(duì)象的名稱,class是工廠類,也就實(shí)現(xiàn)實(shí)例化類的靜態(tài)方法所屬的類,factory-method是實(shí)現(xiàn)實(shí)例化類的靜態(tài)方法。

          然后按照正常的調(diào)用方法去調(diào)用即可:

          public void instanceSpring(){
                          //加載spring配置文件
          ApplicationContext ac = new ClassPathXmlApplicationContext(
          new String[]{
          "/conf/applicationContext.xml"
          });
          //調(diào)用getBean方法取得被實(shí)例化的對(duì)象。
          PersonServiceBean psb = (PersonServiceBean) ac.getBean("personService1");
          psb.save();
          }

          三、使用實(shí)例化工廠方法實(shí)例化。

          這個(gè)方法和上面的方法不同之處在與使用該實(shí)例化方式工廠方法不需要是靜態(tài)的,但是在spring的配置文件中需要配置更多的內(nèi)容,,首先創(chuàng)建工廠類及工廠方法:

          package cn.mytest.service.impl;
          /**
          *創(chuàng)建工廠類
          *
          */
          public class PersonServiceFactory {
              //創(chuàng)建靜態(tài)方法
          public PersonServiceBean createPersonServiceBean1(){
                   //返回實(shí)例化的類的對(duì)象
          return new PersonServiceBean();
          }
          }
          然后再去配置spring配置文件,配置的方法和上面有點(diǎn)不同,這里也是關(guān)鍵所在
          <!--applicationContext.xml配置:-->
          <bean id="personServiceFactory" class="cn.mytest.service.impl.PersonServiceFactory"></bean>
          <bean id="personService2" factory-bean="personServiceFactory" factory-method="createPersonServiceBean1"></bean>

           這里需要配置兩個(gè)bean,第一個(gè)bean使用的構(gòu)造器方法實(shí)例化工廠類,第二個(gè)bean中的id是實(shí)例化對(duì)象的名稱,factory-bean對(duì)應(yīng)的被實(shí)例化的工廠類的對(duì)象名稱,也就是第一個(gè)bean的id,factory-method是非靜態(tài)工廠方法。

           

           

          然后按照正常的調(diào)用方法去調(diào)用即可:

          public void instanceSpring(){
                          //加載spring配置文件
          ApplicationContext ac = new ClassPathXmlApplicationContext(
          new String[]{
          "/conf/applicationContext.xml"
          });
          //調(diào)用getBean方法取得被實(shí)例化的對(duì)象。
          PersonServiceBean psb = (PersonServiceBean) ac.getBean("personService2");
          psb.save();
          }
          posted @ 2015-04-20 15:01 abin 閱讀(473) | 評(píng)論 (0)編輯 收藏

          所謂原子操作,就是"不可中斷的一個(gè)或一系列操作" 。

          硬件級(jí)的原子操作:
          在單處理器系統(tǒng)(UniProcessor)中,能夠在單條指令中完成的操作都可以認(rèn)為是" 原子操作",因?yàn)橹袛嘀荒馨l(fā)生于指令之間。這也是某些CPU指令系統(tǒng)中引入了test_and_set、test_and_clear等指令用于臨界資源互斥的原因。

          在對(duì)稱多處理器(Symmetric Multi-Processor)結(jié)構(gòu)中就不同了,由于系統(tǒng)中有多個(gè)處理器在獨(dú)立地運(yùn)行,即使能在單條指令中完成的操作也有可能受到干擾。

          在x86 平臺(tái)上,CPU提供了在指令執(zhí)行期間對(duì)總線加鎖的手段。CPU芯片上有一條引線#HLOCK pin,如果匯編語(yǔ)言的程序中在一條指令前面加上前綴"LOCK",經(jīng)過匯編以后的機(jī)器代碼就使CPU在執(zhí)行這條指令的時(shí)候把#HLOCK pin的電位拉低,持續(xù)到這條指令結(jié)束時(shí)放開,從而把總線鎖住,這樣同一總線上別的CPU就暫時(shí)不能通過總線訪問內(nèi)存了,保證了這條指令在多處理器環(huán)境中的

          原子性。
          軟件級(jí)的原子操作:
          軟件級(jí)的原子操作實(shí)現(xiàn)依賴于硬件原子操作的支持。
          對(duì)于linux而言,內(nèi)核提供了兩組原子操作接口:一組是針對(duì)整數(shù)進(jìn)行操作;另一組是針對(duì)單獨(dú)的位進(jìn)行操作。
          2.1. 原子整數(shù)操作
          針對(duì)整數(shù)的原子操作只能對(duì)atomic_t類型的數(shù)據(jù)處理。這里沒有使用C語(yǔ)言的int類型,主要是因?yàn)椋?/span>

          1) 讓原子函數(shù)只接受atomic_t類型操作數(shù),可以確保原子操作只與這種特殊類型數(shù)據(jù)一起使用

          2) 使用atomic_t類型確保編譯器不對(duì)相應(yīng)的值進(jìn)行訪問優(yōu)化

          3) 使用atomic_t類型可以屏蔽不同體系結(jié)構(gòu)上的數(shù)據(jù)類型的差異。盡管Linux支持的所有機(jī)器上的整型數(shù)據(jù)都是32位,但是使用atomic_t的代碼只能將該類型的數(shù)據(jù)當(dāng)作24位來(lái)使用。這個(gè)限制完全是因?yàn)樵赟PARC體系結(jié)構(gòu)上,原子操作的實(shí)現(xiàn)不同于其它體系結(jié)構(gòu):32位int類型的低8位嵌入了一個(gè)鎖,因?yàn)镾PARC體系結(jié)構(gòu)對(duì)原子操作缺乏指令級(jí)的支持,所以只能利用該鎖來(lái)避免對(duì)原子類型數(shù)據(jù)的并發(fā)訪問。

          原子整數(shù)操作最常見的用途就是實(shí)現(xiàn)計(jì)數(shù)器。原子整數(shù)操作列表在中定義。原子操作通常是內(nèi)斂函數(shù),往往通過內(nèi)嵌匯編指令來(lái)實(shí)現(xiàn)。如果某個(gè)函數(shù)本來(lái)就是原子的,那么它往往會(huì)被定義成一個(gè)宏。

          在編寫內(nèi)核時(shí),操作也簡(jiǎn)單:

          atomic_t use_cnt;

          atomic_set(&use_cnt, 2);

          atomic_add(4, &use_cnt);

          atomic_inc(use_cnt);

          2.2. 原子性與順序性

          原子性確保指令執(zhí)行期間不被打斷,要么全部執(zhí)行,要么根本不執(zhí)行。而順序性確保即使兩條或多條指令出現(xiàn)在獨(dú)立的執(zhí)行線程中,甚至獨(dú)立的處理器上,它們本該執(zhí)行的順序依然要保持。

          2.3. 原子位操作

          原子位操作定義在文件中。令人感到奇怪的是位操作函數(shù)是對(duì)普通的內(nèi)存地址進(jìn)行操作的。原子位操作在多數(shù)情況下是對(duì)一個(gè)字長(zhǎng)的內(nèi)存訪問,因而位號(hào)該位于0-31之間(在64位機(jī)器上是0-63之間),但是對(duì)位號(hào)的范圍沒有限制。

          編寫內(nèi)核代碼,只要把指向了你希望的數(shù)據(jù)的指針給操作函數(shù),就可以進(jìn)行位操作了:

          unsigned long word = 0;

          set_bit(0, &word); /*第0位被設(shè)置*/

          set_bit(1, &word); /*第1位被設(shè)置*/

          clear_bit(1, &word); /*第1位被清空*/

          change_bit(0, &word); /*翻轉(zhuǎn)第0位*/

          為什么關(guān)注原子操作?
          1)在確認(rèn)一個(gè)操作是原子的情況下,多線程環(huán)境里面,我們可以避免僅僅為保護(hù)這個(gè)操作在外圍加上性能開銷昂貴的鎖。
          2)借助于原子操作,我們可以實(shí)現(xiàn)互斥鎖。
          3)借助于互斥鎖,我們可以把一些列操作變?yōu)樵硬僮鳌?/span>

          GNU C中x++是原子操作嗎?
          答案不是。x++由3條指令完成。x++在單CPU下不是原子操作。
          對(duì)應(yīng)3條匯編指令
          movl x, %eax
          addl $1, %eax
          movl %eax, x
          在vc2005下對(duì)應(yīng)
          ++x;
          004232FA mov eax,dword ptr [x]
          004232FD add eax,1
          00423300 mov dword ptr [x],eax
          仍然是3條指令。
          所以++x,x++等都不是原子操作。因其步驟包括了從內(nèi)存中取x值放入寄存器,加寄存器,把值寫入內(nèi)存三個(gè)指令。

          如何實(shí)現(xiàn)x++的原子性?
          在單處理器上,如果執(zhí)行x++時(shí),禁止多線程調(diào)度,就可以實(shí)現(xiàn)原子。因?yàn)閱翁幚淼亩嗑€程并發(fā)是偽并發(fā)。
          在多處理器上,需要借助cpu提供的Lock功能。鎖總線。讀取內(nèi)存值,修改,寫回內(nèi)存三步期間禁止別的CPU訪問總線。同時(shí)我估計(jì)使用Lock指令鎖總線的時(shí)候,OS也不會(huì)把當(dāng)前線程調(diào)度走了。要是調(diào)走了,那就麻煩了。

          在多處理器系統(tǒng)中存在潛在問題的原因是:
          不使用LOCK指令前綴鎖定總線的話,在一次內(nèi)存訪問周期中有可能其他處理器會(huì)產(chǎn)生異常或中斷,而在異常處理中有可能會(huì)修改尚未寫入的地址,這樣當(dāng)INC操作完成后會(huì)產(chǎn)生無(wú)效數(shù)據(jù)(覆蓋了前面的修改)。

          spinlock 用于CPU同步, 它的實(shí)現(xiàn)是基于CPU鎖定數(shù)據(jù)總線的指令.
          當(dāng)某個(gè)CPU鎖住數(shù)據(jù)總線后, 它讀一個(gè)內(nèi)存單元(spinlock_t)來(lái)判斷這個(gè)spinlock 是否已經(jīng)被別的CPU鎖住. 如果否, 它寫進(jìn)一個(gè)特定值, 表示鎖定成功, 然后返回. 如果是, 它會(huì)重復(fù)以上操作直到成功, 或者spin次數(shù)超過一個(gè)設(shè)定值. 鎖定數(shù)據(jù)總線的指令只能保證一個(gè)機(jī)器指令內(nèi), CPU獨(dú)占數(shù)據(jù)總線.
          單CPU當(dāng)然能用spinlock, 但實(shí)現(xiàn)上無(wú)需鎖定數(shù)據(jù)總線.

          spinlock在鎖定的時(shí)候,如果不成功,不會(huì)睡眠,會(huì)持續(xù)的嘗試,單cpu的時(shí)候spinlock會(huì)讓其它process動(dòng)不了.
          posted @ 2015-04-20 14:02 abin 閱讀(377) | 評(píng)論 (0)編輯 收藏

          僅列出標(biāo)題
          共50頁(yè): 上一頁(yè) 1 2 3 4 5 6 7 8 9 下一頁(yè) Last 
          主站蜘蛛池模板: 昌图县| 漳州市| 凤城市| 岱山县| 昔阳县| 宕昌县| 衡山县| 万荣县| 广德县| 耿马| 岳阳县| 图木舒克市| 红河县| 高碑店市| 嘉定区| 田阳县| 晋州市| 天气| 红桥区| 扬中市| 广德县| 泽州县| 合阳县| 岗巴县| 蒙阴县| 漠河县| 乌苏市| 荆州市| 新巴尔虎左旗| 登封市| 永登县| 桃源县| 沁水县| 红安县| 宁夏| 平阴县| 泾阳县| 绩溪县| 开平市| 江孜县| 定西市|