pbootcms网站模板|日韩1区2区|织梦模板||网站源码|日韩1区2区|jquery建站特效-html5模板网

反序列化后哈希圖變慢 - 為什么?

Hashmap slower after deserialization - Why?(反序列化后哈希圖變慢 - 為什么?)
本文介紹了反序列化后哈希圖變慢 - 為什么?的處理方法,對大家解決問題具有一定的參考價值,需要的朋友們下面隨著小編來一起學習吧!

問題描述

我有一個相當大的 Hashmap (~250MB).創建它大約需要 50-55 秒,所以我決定將它序列化并保存到一個文件中.現在從文件中讀取大約需要 16-17 秒.

I have a pretty large Hashmap (~250MB). Creating it takes about 50-55 seconds, so I decided to serialize it and save it to a file. Reading from the file takes about 16-17 seconds now.

唯一的問題是這種方式的查找速度似乎較慢.我一直以為hashmap是從文件中讀入內存的,所以性能應該和我自己創建hashmap的情況是一樣的吧?這是我用來將哈希圖讀入文件的代碼:

The only problem is that lookups seems to be slower this way. I always thought that the hashmap is read from the file into the memory, so the performance should be the same compared to the case when I create the hashmap myself, right? Here is the code I am using to read the hashmap into a file:

File file = new File("omaha.ser");
FileInputStream f = new FileInputStream(file);
ObjectInputStream s = new ObjectInputStream(new BufferedInputStream(f));
omahaMap = (HashMap<Long, Integer>) s.readObject();
s.close();

當我自己創建哈希圖時,3 億次查找大約需要 3.1 秒,而當我從文件中讀取相同的哈希圖時,大約需要 8.5 秒.有人知道為什么嗎?我是否忽略了一些明顯的東西?

300 million lookups take about 3.1 seconds when I create the hashmap myself, and about 8.5 seconds when I read the same hashmap from file. Does anybody have an idea why? Am I overlooking something obvious?

我只是通過 System.nanotime() 來測量"時間,因此沒有使用適當的基準測試方法.代碼如下:

I "measured" the time by just taking the time with System.nanotime(), so no proper benchmark method used. Here is the code:

public class HandEvaluationTest
{
    public static void Test()
    {

        HandEvaluation.populate5Card();
        HandEvaluation.populate9CardOmaha();


        Card[] player1cards = {new Card("4s"), new Card("2s"), new Card("8h"), new Card("4d")};
        Card[] player2cards = {new Card("As"), new Card("9s"), new Card("6c"), new Card("2h")};
        Card[] player3cards = {new Card("9h"), new Card("7h"), new Card("Kc"), new Card("Kh")};
        Card[] table = {new Card("2d"), new Card("2c"), new Card("3c"), new Card("5c"), new Card("4h")};


        int j=0, k=0, l=0;
        long startTime = System.nanoTime();
        for(int p=0; p<100000000; p++)    {
           j = HandEvaluation.handEval9Hash(player1cards, table);
            k = HandEvaluation.handEval9Hash(player2cards, table);
            l = HandEvaluation.handEval9Hash(player3cards, table);

        }
        long estimatedTime = System.nanoTime() - startTime;
        System.out.println("Time needed: " + estimatedTime*Math.pow(10,-6) + "ms");
        System.out.println("Handstrength Player 1: " + j);
        System.out.println("Handstrength Player 2: " + k);
        System.out.println("Handstrength Player 3: " + l);
    }
}

大的 hashmap 工作在 HandEvaluation.populate9CardOmaha() 中完成.5 張牌很小.大一號的代碼:

The big hashmap work is done in HandEvaluation.populate9CardOmaha(). The 5-card one is small. The code for the big one:

 public static void populate9CardOmaha()
        {

            //Check if the hashmap is already there- then just read it and exit
            File hashmap = new File("omaha.ser");
            if(hashmap.exists())
            {
                try
                {
                    File file = new File("omaha.ser");
                    FileInputStream f = new FileInputStream(file);
                    ObjectInputStream s = new ObjectInputStream(new BufferedInputStream(f));
                    omahaMap = (HashMap<Long, Integer>) s.readObject();
                    s.close();
                }
                catch(IOException ioex) {ioex.printStackTrace();}
                catch(ClassNotFoundException cnfex)
                {
                    System.out.println("Class not found");
                    cnfex.printStackTrace();
                    return;
                }
                return;
            }

    // if it's not there, populate it yourself
    ... Code for populating hashmap ...
    // and then save it to file
          (

            try
            {
                File file = new File("omaha.ser");
                FileOutputStream f = new FileOutputStream(file);
                ObjectOutputStream s = new ObjectOutputStream(new BufferedOutputStream(f));
                s.writeObject(omahaMap);
                s.close();
            }
            catch(IOException ioex) {ioex.printStackTrace();}
        }

當我自己填充它時(= 文件不在此處),HandEvaluationTest.Test() 中的查找大約需要 8 秒而不是 3 秒.也許這只是我測量經過時間的非常天真的方式?

When i am populating it myself (= file is not here), lookups in the HandEvaluationTest.Test() take about 8 seconds instead of 3. Maybe it's just my very naive way of measuring the time elapsed?

推薦答案

這個問題很有意思,所以我自己寫了一個測試用例來驗證一下.我發現實時查找與從序列化文件加載的查找速度沒有差異.任何有興趣運行它的人都可以在文章末尾找到該程序.

This question was interesting, so I wrote my own test case to verify it. I found no difference in speed for a live lookup Vs one that was loaded from a serialized file. The program is available at the end of the post for anyone interested in running it.

  • 使用 JProfiler 監控方法.
  • 序列化文件與您的類似.~ 230 MB.
  • 在沒有任何序列化的情況下在內存中查找花費 1210 毫秒

  • 序列化地圖并再次讀取它們后,查找成本保持不變(幾乎 - 1224 毫秒)

  • 對探查器進行了調整,以在兩種情況下都增加最小的開銷.
  • 這是在 Java(TM) SE 運行時環境(內部版本 1.6.0_25-b06)/4 個 1.7 Ghz 運行的 CPU/4G??B Ram 800 上測量的兆赫

測量很棘手.我自己注意到了您描述的 8 秒 查找時間,但猜猜我在發生這種情況時還注意到了什么.

Measuring is tricky. I myself noticed the 8 second lookup time that you described, but guess what else I noticed when that happened.

您的測量結果可能也反映了這一點.如果您單獨隔離 Map.get() 的測量值,您會發現結果具有可比性.

Your measurements are probably picking that up too. If you isolate the measurements of Map.get() alone you'll see that the results are comparable.

public class GenericTest
{
    public static void main(String... args)
    {
        // Call the methods as you please for a live Vs ser <-> de_ser run
    }

    private static Map<Long, Integer> generateHashMap()
    {
        Map<Long, Integer> map = new HashMap<Long, Integer>();
        final Random random = new Random();
        for(int counter = 0 ; counter < 10000000 ; counter++)
        {
            final int value = random.nextInt();
            final long key = random.nextLong();
            map.put(key, value);
        }
        return map;
    }

    private static void lookupItems(int n, Map<Long, Integer> map)
    {
        final Random random = new Random();
        for(int counter = 0 ; counter < n ; counter++)
        {
            final long key = random.nextLong();
            final Integer value = map.get(key);
        }
    }

    private static void serialize(Map<Long, Integer> map)
    {
        try
        {
            File file = new File("temp/omaha.ser");
            FileOutputStream f = new FileOutputStream(file);
            ObjectOutputStream s = new ObjectOutputStream(new BufferedOutputStream(f));
            s.writeObject(map);
            s.close();
        }
        catch (Exception e)
        {
            e.printStackTrace();
        }
    }

    private static Map<Long, Integer> deserialize()
    {
        try
        {
            File file = new File("temp/omaha.ser");
            FileInputStream f = new FileInputStream(file);
            ObjectInputStream s = new ObjectInputStream(new BufferedInputStream(f));
            HashMap<Long, Integer> map = (HashMap<Long, Integer>) s.readObject();
            s.close();
            return map;
        }
        catch (Exception e)
        {
            throw new RuntimeException(e);
        }
    }
}

這篇關于反序列化后哈希圖變慢 - 為什么?的文章就介紹到這了,希望我們推薦的答案對大家有所幫助,也希望大家多多支持html5模板網!

【網站聲明】本站部分內容來源于互聯網,旨在幫助大家更快的解決問題,如果有圖片或者內容侵犯了您的權益,請聯系我們刪除處理,感謝您的支持!

相關文檔推薦

Convert List of Strings into Map using Java-8 Streams API(使用 Java-8 Streams API 將字符串列表轉換為 Map)
Getting data from JSON(從 JSON 獲取數據)
java linkedhashmap iteration(javalinkedhashmap迭代)
Converting a list of objects to Map(將對象列表轉換為 Map)
Create a HashMap with a fixed Key corresponding to a HashSet. point of departure(用一個固定的Key對應一個HashSet創建一個HashMap.出發點)
HttpMessageConverter exception : RestClientException: Could not write request: no suitable HttpMessageConverter found(HttpMessageConverter 異常:RestClientException:無法寫入請求:找不到合適的 HttpMessageConverter) - IT屋-程序員
主站蜘蛛池模板: 干粉砂浆设备_干混砂浆生产线_腻子粉加工设备_石膏抹灰砂浆生产成套设备厂家_干粉混合设备_砂子烘干机--郑州铭将机械设备有限公司 | 标准品网_标准品信息网_【中检计量】| 贝壳粉涂料-内墙腻子-外墙腻子-山东巨野七彩贝壳漆业中心 | 柔软云母板-硬质-水位计云母片组件-首页-武汉长丰云母绝缘材料有限公司 | SDG吸附剂,SDG酸气吸附剂,干式酸性气体吸收剂生产厂家,超过20年生产使用经验。 - 富莱尔环保设备公司(原名天津市武清县环保设备厂) | 筛分机|振动筛分机|气流筛分机|筛分机厂家-新乡市大汉振动机械有限公司 | 海峰资讯 - 专注装饰公司营销型网站建设和网络营销培训 | 环保袋,无纺布袋,无纺布打孔袋,保温袋,环保袋定制,环保袋厂家,环雅包装-十七年环保袋定制厂家 | MTK核心板|MTK开发板|MTK模块|4G核心板|4G模块|5G核心板|5G模块|安卓核心板|安卓模块|高通核心板-深圳市新移科技有限公司 | 铸钢件厂家-铸钢齿轮-减速机厂家-淄博凯振机械有限公司 | 烟气在线监测系统_烟气在线监测仪_扬尘检测仪_空气质量监测站「山东风途物联网」 | 泰国试管婴儿_泰国第三代试管婴儿_泰国试管婴儿费用/多少钱_孕泰来 | 交变/复合盐雾试验箱-高低温冲击试验箱_安奈设备产品供应杭州/江苏南京/安徽马鞍山合肥等全国各地 | 山东风淋室_201/304不锈钢风淋室净化设备厂家-盛之源风淋室厂家 翻斗式矿车|固定式矿车|曲轨侧卸式矿车|梭式矿车|矿车配件-山东卓力矿车生产厂家 | 外贸网站建设-外贸网站设计制作开发公司-外贸独立站建设【企术】 | 海外仓系统|国际货代系统|退货换标系统|WMS仓储系统|海豚云 | 暖气片十大品牌厂家_铜铝复合暖气片厂家_暖气片什么牌子好_欣鑫达散热器 | 内六角扳手「厂家」-温州市威豪五金工具有限公司 | 背压阀|减压器|不锈钢减压器|减压阀|卫生级背压阀|单向阀|背压阀厂家-上海沃原自控阀门有限公司 本安接线盒-本安电路用接线盒-本安分线盒-矿用电话接线盒-JHH生产厂家-宁波龙亿电子科技有限公司 | 黑龙江京科脑康医院-哈尔滨精神病医院哪家好_哈尔滨精神科医院排名_黑龙江精神心理病专科医院 | 雪花制冰机(实验室雪花制冰机)百科 | 西安文都考研官网_西安考研辅导班_考研培训机构_西安在职考研培训 | 步进驱动器「一体化」步进电机品牌厂家-一体式步进驱动 | 称重传感器,测力传感器,拉压力传感器,压力变送器,扭矩传感器,南京凯基特电气有限公司 | 照相馆预约系统,微信公众号摄影门店系统,影楼管理软件-盟百网络 | 济南ISO9000认证咨询代理公司,ISO9001认证,CMA实验室认证,ISO/TS16949认证,服务体系认证,资产管理体系认证,SC食品生产许可证- 济南创远企业管理咨询有限公司 郑州电线电缆厂家-防火|低压|低烟无卤电缆-河南明星电缆 | 高速龙门架厂家_监控杆_多功能灯杆_信号灯杆_锂电池太阳能路灯-鑫世源照明 | 精益专家 - 设备管理软件|HSE管理系统|设备管理系统|EHS安全管理系统 | 越南专线物流_东莞国际物流_东南亚专线物流_行通物流 | 承插管件_不锈钢承插管件_锻钢高压管件-温州科正阀门管件有限公司 | 智能终端_RTU_dcm_北斗星空自动化科技 | RTO换向阀_VOC高温阀门_加热炉切断阀_双偏心软密封蝶阀_煤气蝶阀_提升阀-湖北霍科德阀门有限公司 | 河南道路标志牌_交通路标牌_交通标志牌厂家-郑州路畅交通 | 不锈钢散热器,冷却翅片管散热器厂家-无锡市烨晟化工装备科技有限公司 | 制丸机,小型中药制丸机,全自动制丸机价格-甘肃恒跃制药设备有限公司 | 微型驱动系统解决方案-深圳市兆威机电股份有限公司 | 缝纫客| 齿式联轴器-弹性联轴器-联轴器厂家-江苏诺兴传动联轴器制造有限公司 | KBX-220倾斜开关|KBW-220P/L跑偏开关|拉绳开关|DHJY-I隔爆打滑开关|溜槽堵塞开关|欠速开关|声光报警器-山东卓信有限公司 | 电缆桥架生产厂家_槽式/梯式_热镀锌线槽_广东东莞雷正电气 | 合肥注册公司|合肥代办营业执照、2024注册公司流程 |