添加到HashMap,其Value部分是另一个HashMap

时间:2014-04-20 00:07:55

标签: java hashmap

很抱歉,如果这是一个noob问题,但我想知道如何在for循环中为以下地图添加值:

private void filterSnakes() {
    Map<Integer, Map<Integer, Integer>> mapSnakes
            = new HashMap<Integer, Map<Integer, Integer>>();

    int coutner = 0;

    for(int i = 0; i < mGameAssets.length; i++)
    {
        if(mGameAssets[i].getAssetType().isSnake()){ //check if the asset is snake
             mapSnakes.put(++coutner, i,mGameAssets[i].getDamage() );
        }
    }
}

我的意思是我如何在mapSnakes中添加一个新条目,关键部分是可以的,但是Value部分本身是一个Map呢?

3 个答案:

答案 0 :(得分:2)

您需要先创建或获取嵌套地图:

++counter;
if (!mapSnakes.containsKey(counter)) {
  mapSnakes.put(counter, new HashMap<Integer, Integer>());
}

mapSnakes.get(counter).put(i,mGameAssets[i].getDamage());

在上面的代码中,如果它不存在,则创建嵌套映射。接下来,您将获得带有mapSnakes.get(counter)的地图,并将内容添加到嵌套地图中。

答案 1 :(得分:2)

您已将地图声明为从整数到地图的映射。因此

    mapSnakes.put(++counter, i,mGameAssets[i].getDamage() );

需要是这样的:

    Map<Integer, Integer> submap = ...
    mapSnakes.put(++counter, submap);

...或者可能像@dimoniy的答案。 (目前尚不清楚,因为你实际上没有指定如何你希望数据结构被初始化。我猜,但我今天早上不玩那个游戏。)


其他要点是:

  • 这看起来像是一个糟糕的OO设计。 Java中基本类型等地图的地图具有“代码味道”。通常,这意味着您应该已经定义了一些应用程序类。

  • 地图是相当昂贵的数据结构,无论是在内存使用还是在时间上。无论何时你必须使用Integer而不是int,你都会因拳击和拆箱而产生间接费用。

答案 2 :(得分:1)

您必须将其分为两个步骤:

  1. 创建要插入的地图。
  2. 将其插入mapSnakes
  3. 像这样:

    if(mGameAssets[i].getAssetType().isSnake()){ //check if the asset is snake
        // Step 1
        Map<Integer,Integer> assetMap = new HashMap<Integer,Integer>();
        assetMap.put(i, mGameAssets[i].getDamage());
        // Step 2
        mapSnakes.put(++coutner, assetMap);
    }
    

    虽然您的设计看起来有点奇怪,但您确定这是您想要做的吗?


    回复你的评论,你说你想知道两件事:

    • mGameAsset中有多少只蛇。
    • 它们是什么指数以及它们的损害是什么。

    你可以使用一张地图,一张将索引映射到蛇本身的地图,例如假设您的资产属于Asset类:

    private void filterSnakes () {
    
        // maps asset index => snake
        Map<Integer,Asset> snakes = new HashMap<Integer,Asset>(); 
    
        // find all the snakes:
        for (int i = 0; i < mGameAssets.length; ++ i) {
            if (mGameAssets[i].getAssetType().isSnake())
                snakes.put(i, mGameAssets[i]);
        }
    
        // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
    
        // now we can process their indices and damage, for example:
        for (Map.Entry<Integer,Asset> snakeEntry : snakes.entrySet()) {
            int index = snakeEntry.getKey();
            int damage = snakeEntry.getValue().getDamage();
            System.out.println("Snake at " + index + " damage is " + damage);
        }
    
        // and we can find the number of snakes too:
        int snakeCount = snakes.size();
        System.out.println("There are " + snakeCount + " snakes.");
    
        // bonus: we can even just get a generic collection of the snakes:
        Collection<Asset> snakesOnly = snakes.values();
    
    }
    

    如果您想保留广告订单,请使用LinkedHashMap

    另一种选择是使用ArrayList或其他List代替Map;如果你这样做,你将不得不制作一个可以容纳索引和蛇的小类(类似于Map.Entry<Integer,Asset>,那么你可以为每个蛇条目创建一个小类并保持一个{ {1}}那些。更多的工作,但有一个优势,就是没有地图的开销(这对你来说可能或不重要)。