简体   繁体   English

在迭代期间更改 HashMap 键

[英]Changing HashMap keys during iteration

is it possible to change keys of a the same HashMap instance during iteration ?是否可以在迭代期间更改同一个 HashMap 实例的键? Because map entry set don't have a method entry.setKey().因为地图条目集没有方法 entry.setKey()。 Now what I can think off is create another HashMap...现在我能想到的是创建另一个 HashMap ......

MultipartParsingResult parsingResult = parseRequest(request);

Map<String, String[]> mpParams = parsingResult.getMultipartParameters();
Map<String, String[]> mpParams2 = new HashMap<String, String[]>();

Iterator<Entry<String,String[]>> it = mpParams.entrySet().iterator();

while (it.hasNext()) {
    Entry<String,String[]> entry = it.next();
    String name = entry.getKey();

    if (name.startsWith(portletNamespace)) {
        mpParams2.put(name.substring(portletNamespace.length(), name.length()), entry.getValue());
    }
    else {
        mpParams2.put(name, entry.getValue());
    }
}

也许这有帮助:

map.put(newkey,map.remove(oldkey));

You should keep information in other collection to modify it after iteration.您应该将信息保留在其他集合中以在迭代后对其进行修改。 You can only remove entry using iterator.remove() during iterator.您只能在迭代器期间使用iterator.remove()删除条目。 HashMap contract forbids mutating it during iteration. HashMap合约禁止在迭代期间对其进行变异。

There are four common types of modification you might want to do to the keys or values in a HashMap.您可能希望对 HashMap 中的键或值进行四种常见的修改。

  1. To change a HashMap key, you look up the value object with get, then remove the old key and put it with the new key.要更改 HashMap 键,请使用 get 查找值对象,然后删除旧键并将其放入新键。
  2. To change the fields in a value object, look the value object up by key with get, then use its setter methods.要更改值对象中的字段,请使用 get 键查找值对象,然后使用其 setter 方法。
  3. To replace the value object in its entirely, just put a new value object at the old key.要完全替换值对象,只需在旧键处放置一个新值对象。
  4. To replace the value object with one based on the old, look the value object up with get, create a new object, copy data over from the old one, then put the new object under the same key.要将值对象替换为基于旧的值对象,请使用 get 查找值对象,创建一个新对象,从旧对象复制数据,然后将新对象放在相同的键下。

Something like this example.像这个例子。

static class Food
    {
    // ------------------------------ FIELDS ------------------------------

    String colour;

    String name;

    float caloriesPerGram;
    // -------------------------- PUBLIC INSTANCE  METHODS --------------------------

    public float getCaloriesPerGram()
        {
        return caloriesPerGram;
        }

    public void setCaloriesPerGram( final float caloriesPerGram )
        {
        this.caloriesPerGram = caloriesPerGram;
        }

    public String getColour()
        {
        return colour;
        }

    public void setColour( final String colour )
        {
        this.colour = colour;
        }

    public String getName()
        {
        return name;
        }

    public void setName( final String name )
        {
        this.name = name;
        }

    public String toString()
        {
        return name + " : " + colour + " : " + caloriesPerGram;
        }

    // --------------------------- CONSTRUCTORS ---------------------------

    Food( final String name, final String colour, final float caloriesPerGram )
        {
        this.name = name;
        this.colour = colour;
        this.caloriesPerGram = caloriesPerGram;
        }
    }

// --------------------------- main() method ---------------------------

/**
 * Sample code to TEST HashMap Modifying
 *
 * @param args not used
 */
public static void main( String[] args )
    {
    // create a new HashMap
    HashMap<String, Food> h = new HashMap<String, Food>( 149
            /* capacity */,
            0.75f
            /* loadfactor */ );

    // add some Food objecs to the HashMap
    // see http://www.calorie-charts.net  for calories/gram
    h.put( "sugar", new Food( "sugar", "white", 4.5f ) );
    h.put( "alchol", new Food( "alcohol", "clear", 7.0f ) );
    h.put( "cheddar", new Food( "cheddar", "orange", 4.03f ) );
    h.put( "peas", new Food( "peas", "green", .81f ) );
    h.put( "salmon", new Food( "salmon", "pink", 2.16f ) );

    // (1) modify the alcohol key to fix the spelling error in the key.
    Food alc = h.get( "alchol" );
    h.put( "alcohol", alc );
    h.remove( "alchol" );

    // (2) modify the value object for sugar key.
    Food sug = h.get( "sugar" );
    sug.setColour( "brown" );
    // do not need to put.

    // (3) replace the value object for the cheddar key
    // don't need to get the old value first.
    h.put( "cheddar", new Food( "cheddar", "white", 4.02f ) );

    // (4) replace the value object for the peas key with object based on previous
    Food peas = h.get( "peas" );
    h.put( "peas", new Food( peas.getName(), peas.getColour(), peas.getCaloriesPerGram() * 1.05f ) );

    // enumerate all the keys in the HashMap in random order
    for ( String key : h.keySet() )
        {
        out.println( key + " = " + h.get( key ).toString() );
        }
    }// end main
}

I hope this helps我希望这有帮助

The best thing to do is to copy the map into a new one with the modifications you want, then return this new maps and destroy the old one.最好的办法是将地图复制到带有您想要的修改的新地图中,然后返回这个新地图并销毁旧地图。 I wonder what's the performance impact of this solution however.但是,我想知道此解决方案的性能影响是什么。

i got to this thread when i needed to change the keys of the map entries.当我需要更改地图条目的键时,我进入了这个线程。 in my case i have a JSON representation in a Map , meaning it can hold map or list of maps, here is the code:就我而言,我在 Map 中有一个 JSON 表示,这意味着它可以保存地图或地图列表,这是代码:

private Map<String,Object> changeKeyMap(Map<String, Object> jsonAsMap) throws InterruptedException {

    Map<String,Object> mapClone = new LinkedHashMap<>();
    for (Map.Entry<String, Object> entry : jsonAsMap.entrySet()) {
        if (Thread.currentThread().isInterrupted()) throw new InterruptedException();
        Object value = entry.getValue();
        if (entry.getValue() instanceof Map) {
            value = changeKeyMap((Map) entry.getValue());
        } else if (isListOfMaps(entry.getValue())) {
            value = changeKeyListOfMaps((List<Map<String, Object>>) entry.getValue());
        }
        String changedKey = changeSingleKey(entry.getKey());
        mapClone.put(changedKey, value);
    }
    return mapClone;
}

private List<Map<String,Object>> changeKeyListOfMaps(List<Map<String,Object>> listOfMaps) throws InterruptedException {
    List<Map<String,Object>> newInnerMapList = new ArrayList<>();
    for(Object singleMapFromArray :listOfMaps){
        Map<String,Object> changeKeyedMap = changeKeyMap((Map<String, Object>) singleMapFromArray);
        newInnerMapList.add(changeKeyedMap);
    }
    return newInnerMapList;
}
private boolean isListOfMaps(Object object) {
    return object instanceof List && !((List) object).isEmpty() && ((List) object).get(0) instanceof Map;
}

private String changeSingleKey(String originalKey) {
    return originalKey + "SomeChange"
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM