java中实现list或set转map的方法
java中实现list或set转map的方法
在开发中我们有时需要将list或set转换为map(比如对象属性中的唯一键作为map的key,对象作为map的value),一般的想法就是new一个map,然后把list或set中的值一个个push到map中。
类似下面的代码:
List<String>stringList=Lists.newArrayList("t1","t2","t3"); Map<String,String>map=Maps.newHashMapWithExpectedSize(stringList.size()); for(Stringstr:stringList){ map.put(str,str); }
是否还有更优雅的写法呢?答案是有的。
guava提供了集合(实现了Iterables接口或Iterator接口)转map的方法,方法定义如下:
/** *Returnsanimmutablemapforwhichthe{@linkMap#values}arethegiven *elementsinthegivenorder,andeachkeyistheproductofinvokinga *suppliedfunctiononitscorrespondingvalue. * *@paramvaluesthevaluestousewhenconstructingthe{@codeMap} *@paramkeyFunctionthefunctionusedtoproducethekeyforeachvalue *@returnamapmappingtheresultofevaluatingthefunction{@code *keyFunction}oneachvalueintheinputcollectiontothatvalue *@throwsIllegalArgumentExceptionif{@codekeyFunction}producesthesame *keyformorethanonevalueintheinputcollection *@throwsNullPointerExceptionifanyelementsof{@codevalues}isnull,or *if{@codekeyFunction}produces{@codenull}foranyvalue */ publicstatic<K,V>ImmutableMap<K,V>uniqueIndex( Iterable<V>values,Function<?superV,K>keyFunction){ returnuniqueIndex(values.iterator(),keyFunction); } /** *Returnsanimmutablemapforwhichthe{@linkMap#values}arethegiven *elementsinthegivenorder,andeachkeyistheproductofinvokinga *suppliedfunctiononitscorrespondingvalue. * *@paramvaluesthevaluestousewhenconstructingthe{@codeMap} *@paramkeyFunctionthefunctionusedtoproducethekeyforeachvalue *@returnamapmappingtheresultofevaluatingthefunction{@code *keyFunction}oneachvalueintheinputcollectiontothatvalue *@throwsIllegalArgumentExceptionif{@codekeyFunction}producesthesame *keyformorethanonevalueintheinputcollection *@throwsNullPointerExceptionifanyelementsof{@codevalues}isnull,or *if{@codekeyFunction}produces{@codenull}foranyvalue *@since10.0 */ publicstatic<K,V>ImmutableMap<K,V>uniqueIndex( Iterator<V>values,Function<?superV,K>keyFunction){ checkNotNull(keyFunction); ImmutableMap.Builder<K,V>builder=ImmutableMap.builder(); while(values.hasNext()){ Vvalue=values.next(); builder.put(keyFunction.apply(value),value); } returnbuilder.build(); }
这样我们就可以很方便的进行转换了,如下:
List<String>stringList=Lists.newArrayList("t1","t2","t3"); Map<String,String>map=Maps.uniqueIndex(stringList,newFunction<String,String>(){ @Override publicStringapply(Stringinput){ returninput; } });
需要注意的是,如接口注释所说,如果Function返回的结果产生了重复的key,将会抛出异常。
java8也提供了转换的方法,这里直接照搬别人博客的代码:
@Test publicvoidconvert_list_to_map_with_java8_lambda(){ List<Movie>movies=newArrayList<Movie>(); movies.add(newMovie(1,"TheShawshankRedemption")); movies.add(newMovie(2,"TheGodfather")); Map<Integer,Movie>mappedMovies=movies.stream().collect( Collectors.toMap(Movie::getRank,(p)->p)); logger.info(mappedMovies); assertTrue(mappedMovies.size()==2); assertEquals("TheShawshankRedemption",mappedMovies.get(1).getDescription()); }
参考:https://www.nhooo.com/article/104114.htm