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

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

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

    隨筆 - 1, 文章 - 0, 評論 - 10, 引用 - 0
    數據加載中……

    經典的IO代碼為什么有資源泄漏?

    最近在開發中,使用到IO操作進行反序列化操作,使用了在各種資料中常見的關于IO操作的經典代碼,在自測和測試人員的測試中都沒有發現任何問題!
    代碼如下

    public ?Object?readObject(File?file)
    ????{
    ????????Object?o?
    = ? null ;
    ????????
    if ?(file.exists())
    ????????{
    ????????????ObjectInputStream?ois?
    = ? null ;
    ????????????
    try
    ????????????{
    ????????????????ois?
    = ? new ?ObjectInputStream( new ?FileInputStream(file));
    ????????????????o?
    = ?ois.readObject();
    ????????????}
    ????????????
    catch ?(Throwable?e)
    ????????????{
    ????????????????e.printStackTrace();
    ????????????}
    ????????????
    finally
    ????????????{
    ????????????????
    if ?(ois? != ? null )
    ????????????????{
    ????????????????????
    try
    ????????????????????{
    ????????????????????????ois.close();
    ????????????????????}
    ????????????????????
    catch ?(IOException?e)
    ????????????????????{
    ????????????????????????e.printStackTrace();
    ????????????????????}
    ????????????????}
    ????????????}????????????
    ????????}
    ????????
    return ?o;
    ????}

    忽然一天測試人員聯系我說這部分代碼導致系統無法啟動,原因僅僅是因為讓該部分代碼不斷的處理一個為序列化文件!
    我仔細分析一下代碼,沒有問題呀,反序列化失敗就直接關閉了ois對象,不可能造成資源泄漏,于是用單步跟蹤的方式
    查看處理非法文件的詳細情況:
    1、創建FileInputStream 沒有問題
    2、創建ObjectInputStream失敗 沒有問題
    3、進入catch塊,打印堆棧 沒有問題
    4、進入finnaly塊,if (ois != null)為false,這時意識到出問題了
    原來創建FileInputStream成功,此時已經申請了資源,但在后續創建ObjectInputStream時失敗,但此時又沒有保存FileInputStream
    的引用,無法釋放資源,最終導致了資源泄漏??磥碓谝院蟮?font color="#0000ff">IO的編程中一定要保存基本流的引用,否則在類似上面的情況
    在轉換流失敗后,無法安全的釋放資源!
    下面為修改后的代碼:

    ?public?Object?readObject(File?file)
    ????{
    ????????Object?o?
    =?null;
    ????????
    if?(file.exists())
    ????????{
    ????????????FileInputStream?fis?
    =?null;
    ????????????ObjectInputStream?ois?
    =?null;
    ????????????
    try
    ????????????{
    ????????????????fis?
    =?new?FileInputStream(file);
    ????????????????ois?
    =?new?ObjectInputStream(fis);
    ????????????????o?
    =?ois.readObject();
    ????????????}
    ????????????
    catch?(Throwable?e)
    ????????????{
    ????????????????e.printStackTrace();
    ????????????}
    ????????????
    finally
    ????????????{
    ????????????????
    if?(fis?!=?null)
    ????????????????{
    ????????????????????
    try
    ????????????????????{
    ????????????????????????fis.close();
    ????????????????????}
    ????????????????????
    catch?(IOException?e)
    ????????????????????{
    ????????????????????????e.printStackTrace();
    ????????????????????}
    ????????????????}
    ????????????}????????????
    ????????}
    ????????
    return?o;
    ????}


    posted on 2006-03-24 21:47 mooninwell 閱讀(1385) 評論(10)  編輯  收藏 所屬分類: Java原創

    評論

    # re: 經典的IO代碼為什么有資源泄漏?  回復  更多評論   

    有一點疑問:
    在文件存在的情況下,在什么情況下會出現fis創建成功而ois創建失???
    另:finally下還是要加上關閉ois的為好。
    2006-03-25 09:14 | 阿偉的技術小巢

    # re: 經典的IO代碼為什么有資源泄漏?  回復  更多評論   

    收到,謝謝分享
    2006-03-25 10:30 | flyfoxs

    # re: 經典的IO代碼為什么有資源泄漏?  回復  更多評論   

    頻繁調用這個方法OPEN/CLOSE STREAM也不是一個好的做法吧?如果一直使用一個ObjectInputStream/ObjectOutputStream就要小心內存泄漏。
    2006-03-25 12:03 | 非魚

    # re: 經典的IO代碼為什么有資源泄漏?  回復  更多評論   

    只要文件存在并且讀的權限就可以成功創建fis,但將fis轉換為ois則文件必需滿足序列化的文件格式。至于ois的關閉,從理論上關閉了基本流fis就不會存在泄漏,而且在實際測試中,window、solaris、aix系統下都沒有問題@阿偉的技術小巢
    2006-03-25 20:37 | mooninwell

    # re: 經典的IO代碼為什么有資源泄漏?  回復  更多評論   

    資源和io流是一一對應的,而且良好的編程習慣應該是對獨占資源應該盡快的釋放,因此處理邏輯應該和從資源中獲取信息相分離@非魚
    2006-03-25 20:40 | mooninwell

    # re: 經典的IO代碼為什么有資源泄漏?  回復  更多評論   

    @mooninwell

    因OIS/OOS使用HANDLETABLE保存被序列化對象的引用,實踐中應注意調用OOS.reset()方法,否則在大量對象序列化時會發生ML。
    2006-03-25 21:44 | 非魚

    # re: 經典的IO代碼為什么有資源泄漏?  回復  更多評論   

    @非魚
    以前工作很少用到IO,特別是序列化部分!今天在你的提醒下,看了一下oos的實現,發現一直使用一個oos/ois的確存在ML的可能性,但我認為這中使用情況在實際應用中很少發生。另:發現OOS的close方法內也包含了reset方法的實現,但ois沒有實現reset方法,會拋異常。
    2006-03-26 00:45 | mooninwell

    # re: 經典的IO代碼為什么有資源泄漏?  回復  更多評論   

    用InputStream代替File作為參數豈不更好?
    2006-03-27 09:49 | hubeicaolei

    # re: 經典的IO代碼為什么有資源泄漏?  回復  更多評論   

    同意樓上的
    2006-03-27 10:07 | nkoffee

    # re: 經典的IO代碼為什么有資源泄漏?  回復  更多評論   

    @mooninwell

    OIS沒有實現reset()方法,是因為它從INPUT流中讀取TC_RESET標志來RESET HANDLE TABLE。這樣可以保證通過網絡SERIALIZATION時不出問題。
    2006-03-28 00:01 | 非魚

    只有注冊用戶登錄后才能發表評論。


    網站導航:
     
    主站蜘蛛池模板: 日韩在线视频播放免费视频完整版 | 亚洲毛片基地日韩毛片基地| 免费无码H肉动漫在线观看麻豆| 亚洲片国产一区一级在线观看| 国产成人无码免费看片软件| 久久精品国产亚洲7777| 亚欧洲精品在线视频免费观看| 亚洲综合最新无码专区| 久青草视频在线观看免费| 亚洲中文字幕无码久久综合网| 国产一级a毛一级a看免费视频 | 国产精品国产免费无码专区不卡 | 成人免费一级毛片在线播放视频 | 久久久99精品免费观看| 久久亚洲精品无码aⅴ大香 | 国产99视频精品免费视频7| 免费国产va在线观看| a级亚洲片精品久久久久久久 | 成人特黄a级毛片免费视频| 国产亚洲情侣久久精品| 精品亚洲视频在线观看| 久草免费手机视频| 亚洲乱码卡一卡二卡三| 四虎精品亚洲一区二区三区| a级毛片在线免费| 亚洲人成人网毛片在线播放| 亚洲成av人片天堂网老年人| 久久久久国产精品免费免费不卡 | 中文字幕乱码一区二区免费| 亚洲精品第五页中文字幕| 午夜精品在线免费观看| 97在线免费视频| 国产亚洲精aa在线看| 久久精品国产亚洲Aⅴ蜜臀色欲| 最近中文字幕完整版免费高清| 亚洲欧洲AV无码专区| 亚洲综合图色40p| 久久久www成人免费毛片 | 日韩av无码久久精品免费| 亚洲国产精品无码久久久秋霞1| 国产亚洲精品成人AA片新蒲金|