posted @ 2012-10-18 23:48 Lv Yuanfang 閱讀(219) | 評論 (0) | 編輯 收藏
2008年9月13日
posted @ 2009-08-16 17:42 Lv Yuanfang 閱讀(3977) | 評論 (0) | 編輯 收藏
工作筆記分享
國慶假期中,粗略看了下Unix網絡編程卷一:套接字API。進一步加深了對Linux、Unix下的socket處理。重點是非阻塞、select多路復用等。記錄筆記幾篇。其他筆記為日常摘錄等。用Google Notebook記錄,特發布和大家分享:
學習筆記:
http://www.google.com/notebook/public/09783819863799136882/BDRihIgoQtMHZkLoh?hl=zh-CN
日常筆記:
http://www.google.com/notebook/public/09783819863799136882/BDRihIgoQlOD34rMh?hl=zh-CN
posted @ 2008-10-02 20:24 Lv Yuanfang 閱讀(237) | 評論 (0) | 編輯 收藏
Java、Linux、C++電子書分享
收藏的一些電子書,跟大家分享下。部分java書有下載鏈接,其他的都是抓圖,都放在Dropbox (文件在線存儲、同步、共享服務,2G免費空間,有windows、linux客戶端,本地文件和服務器共享可以同步)的共享上。需要的可以到Dropbox首頁注冊,告訴我你的帳號后,我可以把共享開放給你。我的帳號:menlong999@gmail.com
Dropbox很不錯,客戶端速度很快,還有版本控制,強烈推薦!
Java
Java與模式: 閻宏的Java設計模式,講的很好JSP2.0技術手冊(部分)
thinking in java 中文版第三版(全):不用多介紹了
j-nio.zip :IBM developerWorks上java.nio教程,很不錯,帶源碼
JUnit.in.Action中文版.pdf
OReilly.Java.I.O.2nd.Edition.May.2006.chm
OReilly.Java.Network.Programming.Third.Edition.Oct.2004.chm
starting-struts2-chinese.pdf:中文的InfoQ Struts2迷你書
Java NIO-Developing High Performance Applications.pdf
Struts 2 in Action.pdf
UML for Java Programmers中文版.pdf
實用J2EE設計模式編程指南.pdf :比較老的,不過也不錯,懷舊一把
Linux
C++
其他
posted @ 2008-09-28 21:21 Lv Yuanfang 閱讀(604) | 評論 (1) | 編輯 收藏
Servlet與模板方法模式
----Head First Pattern之模板方法模式
這 年頭大家都用struts,或者其他MVC框架,很少有人直接用Servlet了吧,但是相信大部分人都應該知道怎么寫Servlet的吧,繼承 HttpServlet類,覆蓋里面的doGet、doPost方法即可,大部分情況下,我們都是對GET和POST一樣處理,一般也就這么寫了:
public MyServlet extends HttpServlet{
public void doGet(HttpServletRequest request, HttpServletResponse response){
// 處理
}
public void doPost()HttpServletRequest request, HttpServletResponse response){
// 不關心get、post請求,因此post處理直接調用get處理
doGet(request, response);
}
}
Servlet只要在web.xml中部署好之后,就可以處理瀏覽器的請求了。上面代碼可以看出來,doGet方法處理瀏覽器的GET請求,doPost處理POST請求。
Servlet是由Tomcat之類的servlet容器來調用處理瀏覽器請求的,并需要集成基類HttpServlet,如果大家查看HttpServlet源碼的時候,就會發現,其實里面有一個
protected void service(HttpServletRequest req, HttpServletResponse resp)
方法,servlet容器實際調用的是service方法,service方法的實現就是根據HTTP請求的類型(GET、POST,還是其他),將處理委派給doGet、doPost等方法,由這些子類的方法來最終處理瀏覽器的請求。
由此可以看出,HttpServlet定義了一個處理的框架或者說模板,實現Servlet只需繼承HttpServlet并實現doGet、doPost等方法即可。
是引出模板方法模式定義的時候了,模板方法模式:在一個方法中定義一個算法的骨架,將某些步驟推遲到子類中實現。模板方法允許子類重新定義算法的某些步驟,而不改變算法的結構。
簡單UML類圖如下:
public abstract Template{
public void final templateMethod(){
step1();
step2();
hook();
}
public abstract void step1();
public abstract void step2();
public void hook(){}
}
這個抽象類,定義了一個算法的骨架,需要step1、step2,都是抽象方法,需要子類來實現。而templateMethod是final的,即不允許子類覆蓋。其中定義了方法的步驟,step1、step2。
如下為具體實現:
public ConcreteTemplate extends Template{
public void step1(){System.out.println("step1");}
public void step2(){System.out.println("step2");}
public void hook(){System.out.println("hook");}
public static void main(String[] args){
Template temp = new ConcreteTemplate();
temp.templateMethod();
}
}
可以看到其中加入了一個hook方法,即鉤子方法。hook方法在抽象類中的實現為空,是留給子類做一些可選的操作。如果某個子類需要一些特殊額外的操作,則可以實現hook方法,當然也可以完全不用理會,因為hook在抽象類中只是空方法而已。
其他擴展:
1.可以定義多個hook方法
2.hook方法可以定義一個返回為boolean的方法,有子類來決定是否調用hook方法。
eg:抽象類的templateMethod可以這樣實現:
public void final templateMethod(){
step1();
step2();
if(allowHook())
hook();
}
public boolean allowHook(){return true;}
public void hook(){}
子類中可以覆蓋allowHook,以決定是否調用hook方法。
3.抽象類定義的步驟,可以有默認實現,而非全是abstract方法。HttpServlet中已經有doGet、doPost等方法的默認實現,大家可以參考其源碼實現。
更好的一個模板方法的例子是Applet,實現自己的Applet,必須繼承自Applet,里面實現init、start、stop、destroy等方法即可。這些方法都是有默認實現的,如果看源碼,可以發現默認實現其實都是空。
了解模板方法模式之后,大家可能意識到Servlet并且完全按照模板方法定義的那樣,而是有一些區別,比如提供默認doGet、doPost的實現等。這都說明,在實際編程中,并非生搬硬套設計模式,而是根據實際,會做些變動或變形,但其本質不變。
不能為了模式而模式。那究竟什么時候需要設計模式呢?個人理解,當你發現你的類有問題的時候,比如有重復代碼了,感覺有些不對勁了,感覺不適應以后的擴充了,這時候不妨考慮下,是不是該設計模式出場了。。
純粹個人理解。。有不當之處,請及時拍磚。。
posted @ 2008-09-17 09:40 Lv Yuanfang 閱讀(1734) | 評論 (0) | 編輯 收藏
有人像我這樣用docs寫,然后發布blog嗎?
posted @ 2008-09-17 00:02 Lv Yuanfang 閱讀(228) | 評論 (0) | 編輯 收藏
移動硬盤與適配器模式
----Head First Pattern之適配器模式
很多人都有移動硬盤,它比U盤容量大的多,體積也小,攜帶方便,用來拷資料、備份都很不錯。并且硬盤價格越來越便宜,120G的移動硬盤現在才300多。
其實移動硬盤里面就是一塊普通的筆記本硬盤,還有一個IDE口(或SATA口,看硬盤的類型了,現在一般都是SATA口即串口,IDE口就是并口)和USB口的轉換卡,用USB線和電腦上的USB口連接起來就行了。
我手頭有一個40G的IDE口筆記本硬盤,想在PC電腦上用,但又不想把電腦拆開插主板的IDE線上。看到電腦上還有很多空閑的USB口,就想能不能讓筆記本硬盤的IDE口連到電腦的USB口?直接連肯定不行,接口不匹配啊。就去電子市場逛了一個下午,發現有一種轉接卡,一頭可以插IDE口,一頭是USB口,能連USB線,USB線就可以連電腦的USB口了。我買了轉接卡回到家,把轉接卡一頭插在筆記本硬盤的IDE口上,另一頭連上USB線,再把USB線連到電腦的USB口上。大功告成,現在我的筆記本硬盤就變成移動硬盤了。轉接卡就是連接IDE口和USB口的適配器。這就是適配器模式。
下面看適配器的UML類圖:
這個類圖有點問題,其實Adaptee應該是一個接口,還有個實現這個接口的ConcreteAdaptee,而Adapter是目標接口,ConcreteAdapter必須實現Adapter,持有一個Adaptee。移動硬盤和適配器模式對應關系如下:
Adapter: USB接口
Adaptee:筆記本硬盤的IDE接口
ConcreteAdapter:轉接卡
總而言之,適配器模式就是把一個接口Adaptee,適配成目標接口Adapter。
某些時候適配器和裝飾模式有點相同之處,但是兩者本質是不一樣的。
Adapter是把所包裝的接口,轉換為另一個接口。而Decorator是給所包裝的接口,添加新的行為或方法。
posted @ 2008-09-15 17:53 Lv Yuanfang 閱讀(310) | 評論 (0) | 編輯 收藏
多線程環境下的單例模式實現
----Head First Pattern之單例模式
單例模式我想大家都比較熟悉,就是在JVM運行期間一個類只有一個實例,任何時候都是取得同一個實例,也就是一個全局變量了。
單例模式分懶漢式和餓漢式,但是懶漢式的單例在多線程環境下會有同步的問題,下面詳細介紹了用3中方法來解決此問題。
單例模式具有以下幾個特點:
1.JVM運行期間有且只有一個實例
2.構造函數是私有的
3.通過一個靜態工廠方法來獲得唯一的實例
4.累內部有一個私有靜態實例,通過靜態工廠方法創建后,每次再調用靜態工廠方法,返回的都是同一個實例
餓漢式:
public class Singleton{
??? private static Singleton uniqueInstance = new Singleton();
??? // 其他實例變量
??? private Singleton(){}
??? public static Singleton getInstance(){
?? ???? return uniqueInstance;
?? ?}
?? ?
??? // 其他方法
}
懶漢式:
public class Singleton{
??? private static Singleton uniqueInstance;
??? // 其他實例變量
??? private Singleton(){}
??? public static Singleton getInstance(){
?? ???? if(uniqueInstance == null){
?? ??? ???? uniqueInstance = new Signleton();
?? ??? ?}
?? ???? return uniqueInstance;
?? ?}
?? ?
??? // 其他方法
}
多線程環境下的單例模式:
上面的代碼就是最基本的單例模式示例代碼。但是懶漢式單例有一個問題,因為要保證有且僅有一個實例,如果在多線程環境下調用Singleton.getInstance(),就可能會有多個實例!為了解決多線程訪問的問題,有3種解決方法供選擇:
1.靜態工廠方法加同步關鍵字,這種方法是在對性能要求不高的情況下采用。
public class Singleton{
??? private static Singleton uniqueInstance;
??? // 其他實例變量
??? private Singleton(){}
??? public static synchronised Singleton getInstance(){
?? ???? if(uniqueInstance == null){
?? ??? ???? uniqueInstance = new Signleton();
?? ??? ?}
?? ???? return uniqueInstance;
?? ?}
?? ?
??? // 其他方法
}
2.始終用餓漢式單例
public class Singleton{
??? private static Singleton uniqueInstance = new Singleton();
??? // 其他實例變量
??? private Singleton(){}
??? public static Singleton getInstance(){
?? ???? return uniqueInstance;
?? ?}
?? ?
??? // 其他方法
}
餓漢式的方法,會依賴于JVM在加載類的時候,就創建唯一的實例。在每個線程訪問getInstance方法前,唯一實例已經被創建。
3.用雙檢查鎖來減少懶漢式中靜態方法getInstance的同步開銷
對public static synchronised Singleton getInstance()的每次調用,都需要同步,而雙檢查鎖的方式只是在第一次創建實例時同步,其他時候并不需要同步。
public class Singleton{
??? private volatile static Singleton uniqueInstance;
??? private Singleton(){}
??? public static Singleton getInstance(){
?? ???? if(uniqueInstance == null){
?? ??? ???? synchronised(Singleton.class){
?? ??? ??? ???? if(uniqueInstance == null){
?? ??? ??? ??? ??? ??? uniqueInstance = new Singleton();
?? ??? ??? ??? ?}
?? ??? ??? ?}
?? ??? ?}
?? ???? return uniqueInstance;
?? ?}
}
如果調用時實例為null,則進入同步區塊,此時再進行判斷,如果還為null,就創建唯一的實例。有可能在一個線程在 if(uniqueInstance == null) 后進入同步區塊前,另一個線程恰好已經創建成功并從同步區塊中出來,這就需要進入同步區塊后,再做uniqueInstance是否為null的判斷。
同時uniqueInstance需要加volatile關鍵字,保證在創建單例實例時,多個線程能正確處理uniqueInstance變量。
注意:
雙檢查鎖的方式在Java1.4及1.4以前版本不能工作!!因此雙檢查鎖只能在Java 5及以上版本才可以使用。
記得Effictive Java中也提到過雙檢查鎖,也說不能在Java1.4中使用。
原因是Java 1.4及以前的JVM中對volatile關鍵字的實現允許對雙檢查鎖不合適的同步。(誰能幫我再深入解釋下?)原文是:
Unfortunately, in Java version 1.4 and earlier, many JVMs contain implementations of the volatile keyword that allow improper synchronization for double-checked locking. If you must use a JVM other than Java 5, consider other methods of implementing your Singleton.
posted @ 2008-09-14 15:40 Lv Yuanfang 閱讀(444) | 評論 (0) | 編輯 收藏
新博開張
最早用的是blogger,不過一直被封。。偶爾解封幾天又被封。現在托奧運的福,已經解了。但愿以后不要再被封。可惡的GFW。。。。
后來用csdn,人夠多,但是也夠爛。一直也沒堅持寫多少東西,都是決心下了,就是懶的動手寫,并且發現寫東西的時候,老是前言不對后尾,前面說什么還沒說完,后來就開始跑題,還有,寫作水平好像越來越差,總感覺一句話寫的不明不白,甚至還有點啰嗦。
始終覺得cnblog還行,界面夠簡單,也夠丑的了。。幾乎都是技術的。平時也有訂閱。今天終于搬來,竟然還需要人工審核,沒想到。
不過寫博,畢竟是為了讓人看,如果有很多評論,或者很多人訂閱rss,肯定非常非常有成就感!!
被人捧也好,被人罵也好,被人褒揚也好,被人拍磚也好,只要有人來看,就是好!!
以后有空還是多寫寫的好。
posted @ 2008-09-14 00:06 Lv Yuanfang 閱讀(170) | 評論 (0) | 編輯 收藏
Head First Pattern之代理模式
遠程代理
虛擬代理
虛擬代理舉的是一個Swing的例子。
我是這么理解的:一個對象的創建非常耗時,通過代理對象去調用,在真實對象創建前,返回一個假的調用,等真實對象創建好了,這時候返回給客戶端的就是一個真實對象的相應方法調用。
也就是延遲加載的問題,Swing例子中,要顯示一個Icon,但是要通過網絡加載一個圖片,在圖片通過網絡加載成功前,先顯示一個“加載中,請稍候...”(如果是真實對象的調用,應該顯示一個圖片),在代理對象中通過后臺線程去加載圖片,加載完了后,再偷偷的把“加載中,請稍候...”的字樣偷偷換成加載成功后的圖片。
沒想到這也算代理模式的一種應用場景。以前有這么在Swing中用過,需要從數據庫中查找數據,但是比較耗時,就先顯示“加載數據中,請稍候...”,等加載完了,再在JTable中顯示出來。如果用代理模式的方式來思考,好像比較的好吧。。
同樣在jsp頁面里,通過ajax來加載數據好像也是這樣的道理,數據沒加載之前就是“加載中...”,加載完了再通過innerHTML來改變顯示,也是同樣的延遲加載問題。
如果用代理模式的方式來考慮,可以定義一個JavaScript類(這個類其實是個代理),這個類有個方法要顯示一些從Server取出的數據,但是調用顯示方法時,后臺數據還沒有加載,就先顯示加載中請稍候之類的文本,這時候通過ajax從Server取數據(創建真實對象),取出來之后在回調函數中更新顯示HTML元素的innerHTML。跟那個Swing的例子一模一樣吧。不過好像JavaScript中好像沒有誰會定義接口、實現、代理對象吧,但是思路其實是一樣的。
不知道這樣理解代理模式,算不算曲解。。。
JDK動態代理
jdk里的動態代理支持,主要是通過java.lang.reflect包中Proxy、InvocationHandler等幾個類來實現的。具體如何實現可參考JDK中文文檔。
使用場合:
好像在在一本Hibernate的書上,對數據庫Connection的close方法調用,用動態代理的方式來攔截,并不真正關閉連接,而是返回到數據庫連接池中。
在Spring中的攔截貌似有些是用動態代理實現的?不過動態代理使用時要基于接口,但是Spring是使用動態生成字節碼的方式?對Spring內部實現機制不熟。。不敢妄自猜測。。等有時間好好研究再來說明。。
和Decorator的比較
posted @ 2008-09-13 23:48 Lv Yuanfang 閱讀(620) | 評論 (0) | 編輯 收藏
Chrome印象
第一印象:
內存占用和速度:
擴展:
目前Chrome還是Beta,沒有提供插件機制,我想用Firefox最大的好處就是插件多吧,其次才是速度快、安全、更符合標準、bug修復速度快等等優點。不過Chrome內置了Google Gears。運行Google Docs和Google Reader可以直接啟用offline功能。這點都是由預謀的。Google Gears提供的離線存儲功能,對以后Google基于Chrome的所謂云計算,應該會提供非常多的支持。并且現在若干個Google服務都已經支持基于Google Gears的離線功能了。
總結:
總的來說,對Google而言,推出自己的瀏覽器,就是為以后Google的未來搭建一個平臺,所有基于Google的服務都很容易就能在Chrome在運行,相當于一個客戶端了。試想全球那么多用戶使用Chrome,Google想在瀏覽器上做點什么手腳,集成點自己的服務,比如Google Toolbar(Chrome竟然沒有集成Toolbar,這點我也比較驚訝,Google Gears已經有了)、或其他的服務,簡直太容易了吧。至于在服務里投放廣告之類,更容易了。不過像微軟已經開始以什么明目起訴Google了。老實說,很明顯的,google在Chrome集成google的搜索服務,就像IE8里集成live搜索一樣(google也投訴了吧,嘿嘿),這應該是必然的事,不過google也得做好被微軟之類起訴壟斷或者應對其他攻擊方式的準備吧。
Google的目標應該會比較長遠。。
posted @ 2008-09-13 23:25 Lv Yuanfang 閱讀(177) | 評論 (0) | 編輯 收藏