Nomad & His Life

          博觀而約取,厚積而薄發
          posts - 15, comments - 88, trackbacks - 0, articles - 0
            BlogJava :: 首頁 :: 新隨筆 :: 聯系 :: 聚合  :: 管理

          以2/8原則指導我們的底層框架設計

          Posted on 2006-07-18 15:18 Nomad 閱讀(1920) 評論(10)  編輯  收藏 所屬分類: Code LifeJava
          原創文章,轉載請注明作者:Nomad,出處: www.jialing.net ?

          ??? 我想很多人都聽說過“2/8原則,有人研究過,這世界上財富的80%集中在20%的人手里,而另外80%的人只擁用20%的財富。實際的商業中,我們應該更關注大客戶,因為客戶里20%的大客戶,對我們貢獻的利潤可能會占到80%,這些都是有統計學基礎的數據。

          ??? 在應用軟件的研發中同樣遵守這個原則,我們寫的20%底層代碼將會起到80%的作用。做過Web項目的人應該都知道,大多數程序都是圍繞增、刪、改、條件查詢等主題實現的,只是需求不同,具體的實現不同罷了。當項目重復性太高的時候,我們開始學習、使用框架技術,比如Hibernate就幫我們提取了很多對數據庫操作的程序,目的也是減少程序員編寫代碼的數量與時間。而框架技術并不能包含我們工作的方方面面,我們依然需要在工作中不斷總結、不斷歸納,猶如Template設計模式,我們需要將重復的工作總結提煉出來,做成一個個模版,以此來不斷簡化我們的工作。所以我們需要以2/8原則指導開發設計,讓更多的活交給框架去工作,讓各種業務流做成模版類,做足底層的工作,將20%的底層代碼發揮出80%貢獻。

          ??? 下面以我熟悉的平臺框架舉個模版的例子。在Hibernate框架下編寫DAO層代碼,我們需要從數據庫中取出數據,以列表形式顯示在頁面上。這個例子將向你展示,只要做好底層工作,上層的業務邏輯就會變得非常簡單(只有短短兩行)。

          ??1//CommonalityObject.java
          ??2
          ??3//用以裝載數據并輸出的Java?Bean
          ??4
          ??5public?class?CommonalityObject?{
          ??6???private?String?str1;
          ??7???private?String?str2;
          ??8???private?String?str3;
          ??9???private?String?str4;
          ?10???private?String?str5;
          ?11???private?String?str6;
          ?12???private?String?str7;
          ?13???private?String?str8;
          ?14
          ?15?
          ?16
          ?17????setters?&?getters
          ?18
          ?19}

          ?20
          ?21//SQLTemplate.java
          ?22
          ?23/**
          ?24?*?報表中執行SQL查詢的模版
          ?25?*?以CommonalityObject來裝載數據,運用反射機制加載返回List
          ?26?*
          ?27?*?@author?李嘉陵
          ?28?*?@since?2006-7-14
          ?29?*/

          ?30
          ?31public?class?SQLTemplate?{
          ?32?
          ?33?private?static?Log?logger?=?LogFactory.getLog(SQLTemplate.class);
          ?34?
          ?35?public?List?getQueryList(String?sql,?Session?session)?throws?DAOException{
          ?36??logger.info(sql);
          ?37??
          ?38??try?{
          ?39???ResultSet?reset?=?getReset(session,sql);
          ?40???logger.info("r="+reset);
          ?41???return?reflectList(reset);
          ?42??}

          ?43??catch?(Exception?e1)?{
          ?44???//?TODO?Auto-generated?catch?block
          ?45???e1.printStackTrace();
          ?46???throw?new?DAOException(e1);
          ?47??}

          ?48?}

          ?49?
          ?50?//?插入SQL獲得相對應的數據集
          ?51?public?ResultSet?getReset(Session?s,?String?sql)?throws?Exception?{
          ?52??
          ?53??Connection?conn?=?null;
          ?54??Statement?stat?=?null;
          ?55??ResultSet?reset?=?null;
          ?56???
          ?57??//獲得連接
          ?58??conn?=?s.connection();
          ?59??
          ?60??//裝載數據塊
          ?61??stat?=?conn.createStatement();
          ?62??//System.out.println("------運行的SQL語句--------"+sql);
          ?63
          ?64??//獲得對應的數據集
          ?65??reset?=?stat.executeQuery(sql);
          ?66?
          ?67??return?reset;
          ?68?}

          ?69?
          ?70?/**
          ?71??*?通過反射機制講ResultSet中的數據以CommonalityObject形式載入List中,最后返回List
          ?72??*?@author?李嘉陵
          ?73??*?@since?2006-7-14
          ?74??*?@param?reset?SQL搜索出來的集合
          ?75??*?@return?List<CommonalityObject>
          ?76??*?@throws?Exception
          ?77??*/

          ?78?public?List?reflectList(ResultSet?reset)?throws?Exception{
          ?79??List?list?=?new?ArrayList();
          ?80??
          ?81??ResultSetMetaData?meta?=?reset.getMetaData();
          ?82??
          ?83??while(reset.next())
          ?84??{
          ?85???CommonalityObject?co?=?new?CommonalityObject();
          ?86???String?tmp="0";
          ?87???
          ?88???for(int?i=1;i<=meta.getColumnCount();i++)?{
          ?89????if?(reset.getString(i)?==?null||?reset.getString(1).equals("")??){
          ?90?????tmp="0";
          ?91????}

          ?92????else{
          ?93?????tmp=reset.getString(i);??????
          ?94????}

          ?95????
          ?96????String?method_name?=?"setStr"+i;?//需要動態調用的函數名
          ?97????Class?cls=co.getClass();?//得到要在其中查找方法的類
          ?98????Class?partypes[]?=?new?Class[]{String.class};?//函數調用的參數類型,這里為String。
          ?99????Method?mth=cls.getMethod(method_name,?partypes);?//得到方法
          100????Object[]?objs=new?Object[]{tmp};?//生成函數要調用的數據,這里為tmp。
          101????mth.invoke(co,?objs);?//調用得到的函數。
          102???}

          103???
          104???list.add(co);
          105??}

          106??
          107??return?list;
          108?}

          109}

          110
          111//最終只要簡單的兩句就能完成報表的輸出工作
          112public?class?OrderQryDAOImpl?extends?BaseDAOImpl?implements?OrderQryDAO?{
          113
          114?public?List?getList(String?cond)?throws?DAOException??{
          115??
          116??//SQL語句
          117??String?sqlStr?=?""?+?cond;
          118
          119??return?new?SQLTemplate().getQueryList(sqlStr,getSession());
          120?????
          121?}

          122}

          看懂了嗎?如果項目中我們需要完成幾十個這樣的報表輸出,有了這樣的底層代碼結構,編寫起來是不是很簡單呢。

          評論

          # re: 以2/8原則指導我們的底層框架設計  回復  更多評論   

          2006-07-18 23:09 by Dragonofson
          你牛比~Hibernate是這樣用~那還不于直接用JDBC

          # re: 以2/8原則指導我們的底層框架設計  回復  更多評論   

          2006-07-19 00:19 by 綠色使者、綠色心情
          確實,還是好好看看Hibernate再說吧

          # re: 以2/8原則指導我們的底層框架設計  回復  更多評論   

          2006-07-19 08:37 by Nomad
          @Dragonofson
          我這里做的是報表任務,和ORM沒有關系。當你的項目數據庫中有五六百張表,你就會發現Hibernate并不能完成所有的活

          # re: 以2/8原則指導我們的底層框架設計  回復  更多評論   

          2006-07-19 09:28 by JustRun
          講的挺好的,不過hibernate中是如何實現的,我現在還不大清楚.
          明白了作者要講的東西,只是自己在使用這種方法的時候,該不該用,什么時候用,如何用還不能夠很好的把握.

          # re: 以2/8原則指導我們的底層框架設計  回復  更多評論   

          2006-07-19 12:10 by 坎井之蛙
          不錯,不錯,希望以后可以看到,兄臺更多的好文章,加油....

          # re: 以2/8原則指導我們的底層框架設計  回復  更多評論   

          2006-07-19 20:17 by badqiu
          一看呀,原來hibernate是個數據庫連接池````

          # re: 以2/8原則指導我們的底層框架設計  回復  更多評論   

          2006-07-20 11:28 by 三寶弟子
          要午餐了,灌幾句!

          e1.printStackTrace();
          throw new DAOException(e1);
          打印異常內容,然后又拋出,好像不好啊

          reset.getString(i) 提出來作為一個local variable把

          reset.getString(i).equals("")
          這個沒問題,不過使用string.getLength()==0 更好些把

          Class cls=co.getClass();
          Class partypes[] = new Class[]{String.class};
          這些放到循環里面,好像很差勁哪!
          會死人的,還是扔到循環外面把

          meta.getColumnCount() 這個不好,
          不如明確使用str1等屬性名稱,
          比如我們的數據庫數據需要導來導去,
          數據庫的表里可能有些字段,本程序根本不會用到....
          這個說錯了,收回!!!!!!僅供參考

          恩,不錯, 加油啊


          # re: 以2/8原則指導我們的底層框架設計  回復  更多評論   

          2006-08-05 00:04 by DrummerStyle
          值得學習,頂了

          # re: 以2/8原則指導我們的底層框架設計  回復  更多評論   

          2006-08-05 00:06 by DrummerStyle
          js的高級用法估計以后都很難接觸到啊。。

          # re: 以2/8原則指導我們的底層框架設計  回復  更多評論   

          2006-08-18 13:03 by 雨人
          分析的不錯,可惜還不理解hibernate
          主站蜘蛛池模板: 监利县| 青龙| 盖州市| 原阳县| 库尔勒市| 万年县| 大荔县| 桂平市| 宜昌市| 广元市| 图片| 酒泉市| 萨嘎县| 晋江市| 吉安县| 财经| 淅川县| 柳河县| 湄潭县| 勃利县| 淮南市| 钦州市| 宿州市| 崇阳县| 正宁县| 苗栗县| 高尔夫| 肇东市| 石城县| 东明县| 潞西市| 马尔康县| 永宁县| 卓资县| 锡林郭勒盟| 同仁县| 九龙坡区| 三穗县| 惠来县| 莒南县| 定日县|