50

そのようなマルチマップ構造は見つかりませんでした...これを実行したい場合は、マップを繰り返し処理して、マルチマップにデータを入力します。他の方法はありますか?

final Map<String, Collection<String>> map = ImmutableMap.<String, Collection<String>>of(
            "1", Arrays.asList("a", "b", "c", "c"));
System.out.println(Multimaps.forMap(map));

final Multimap<String, String> expected = ArrayListMultimap.create();
for (Map.Entry<String, Collection<String>> entry : map.entrySet()) {
    expected.putAll(entry.getKey(), entry.getValue());
}
System.out.println(expected);

最初の結果はです{1=[[a, b, c, c]]}が、私は期待しています{1=[a, b, c, c]}

4

8 に答える 8

49

あなたが持っていると仮定して

Map<String, Collection<String>> map = ...;
Multimap<String, String> multimap = ArrayListMultimap.create();

それなら、これがあなたにできる最善のことだと思います

for (String key : map.keySet()) {
  multimap.putAll(key, map.get(key));
}

またはより最適ですが、読みにくい

for (Entry<String, Collection<String>> entry : map.entrySet()) {
  multimap.putAll(entry.getKey(), entry.getValue());
}
于 2010-06-23T14:42:49.360 に答える
10

この質問は少し古いですが、私は更新された答えを与えると思いました。Java 8を使用すると、次のようなことができます。

ListMultimap<String, String> multimap = ArrayListMultimap.create();
Map<String, Collection<String>> map = ImmutableMap.of(
                           "1", Arrays.asList("a", "b", "c", "c"));
map.forEach(multimap::putAll);
System.out.println(multimap);

これにより{1=[a, b, c, c]}、必要に応じて、が得られるはずです。

于 2016-02-24T17:24:20.750 に答える
8

これは、 StuffGuavaIsMissingクラス用に作成した便利な汎用バージョンです。

/**
 * Creates a Guava multimap using the input map.
 */
public static <K, V> Multimap<K, V> createMultiMap(Map<K, ? extends Iterable<V>> input) {
  Multimap<K, V> multimap = ArrayListMultimap.create();
  for (Map.Entry<K, ? extends Iterable<V>> entry : input.entrySet()) {
    multimap.putAll(entry.getKey(), entry.getValue());
  }
  return multimap;
}

そして不変のバージョン:

/**
 * Creates an Immutable Guava multimap using the input map.
 */
public static <K, V> ImmutableMultimap<K, V> createImmutableMultiMap(Map<K, ? extends Iterable<V>> input) {
  ImmutableMultimap.Builder<K, V> builder = ImmutableMultimap.builder();
  for (Map.Entry<K, ? extends Iterable<V>> entry : input.entrySet()) {
    builder.putAll(entry.getKey(), entry.getValue());
  }
  return builder.build();
}
于 2012-05-04T05:52:46.840 に答える
2

更新:あなたが求めていることについては、にフォールバックする必要があると思いますMultimap.putAll

于 2010-06-22T14:06:25.740 に答える
2

com.google.common.collect.Multimaps.flatteningToMultimapをストリームコレクターとして使用できます。

与えられた地図:

Map<Integer, Collection<String>> map = Map.of(
   1, List.of("a", "b", "c"),
   2, List.of("d", "e", "f"));

次のことができます。

Multimap<Integer, String> multimap = map.entrySet().stream()
    .collect(flatteningToMultimap(Map.Entry::getKey, it -> it.getValue().stream(), HashMultimap::create));
于 2021-03-22T19:45:01.447 に答える
1

GoogleのGuavaライブラリなしの次のコード。キーおよびソートされた順序としてのdouble値に使用されます

Map<Double,List<Object>> multiMap = new TreeMap<Double,List<Object>>();

for( int i= 0;i<15;i++)
{
    List<Object> myClassList = multiMap.get((double)i);
    if(myClassList == null)
    {
        myClassList = new ArrayList<Object>();
        multiMap.put((double) i,myClassList);
    }
    myClassList.add("Value "+ i);
}

List<Object> myClassList = multiMap.get((double)0);
if(myClassList == null)
{
    myClassList = new ArrayList<Object>();
    multiMap.put( (double) 0,myClassList);
}
myClassList.add("Value Duplicate");
for (Map.Entry entry : multiMap.entrySet()) 
{
  System.out.println("Key = " + entry.getKey() + ", Value = " +entry.getValue());
}
于 2013-02-14T15:09:44.663 に答える
1
LinkedListMultimap<String, String> mm = map.entrySet()
    .stream()
    .collect(
        () -> LinkedListMultimap.create(map.size()),
        (m, e) -> m.putAll(e.getKey(), e.getValue()),
        (m1, m2) -> m1.putAll(m2));
于 2018-04-12T07:51:31.443 に答える
0

使用できる別の方法があります。 Multimaps#newMultimap

Listまたはを拡張するコレクションを使用している場合Set、ドキュメントでは特別なメソッドMultimaps#newListMultimapとを使用することをお勧めしMultimaps#newSetMultimapます。

Multimaps.newListMultimap(myMap, ArrayList::new);
Multimaps.newSetMultimap(myMap, HashSet::new);
于 2021-03-15T21:40:27.527 に答える