用Java打印一张地图
我正在寻找漂亮的方式来漂亮地打印Map
。
map.toString()
给我: {key1=value1, key2=value2, key3=value3}
我想在我的地图项值更多的自由,我正在寻找更像这样的东西: key1="value1", key2="value2", key3="value3"
我写了这么一小段代码:
StringBuilder sb = new StringBuilder(); Iterator<Entry<String, String>> iter = map.entrySet().iterator(); while (iter.hasNext()) { Entry<String, String> entry = iter.next(); sb.append(entry.getKey()); sb.append('=').append('"'); sb.append(entry.getValue()); sb.append('"'); if (iter.hasNext()) { sb.append(',').append(' '); } } return sb.toString();
但我相信有一个更优雅和简洁的方式来做到这一点。
或者把你的逻辑放到一个整洁的小class上。
public class PrettyPrintingMap<K, V> { private Map<K, V> map; public PrettyPrintingMap(Map<K, V> map) { this.map = map; } public String toString() { StringBuilder sb = new StringBuilder(); Iterator<Entry<K, V>> iter = map.entrySet().iterator(); while (iter.hasNext()) { Entry<K, V> entry = iter.next(); sb.append(entry.getKey()); sb.append('=').append('"'); sb.append(entry.getValue()); sb.append('"'); if (iter.hasNext()) { sb.append(',').append(' '); } } return sb.toString(); } }
用法:
Map<String, String> myMap = new HashMap<String, String>(); System.out.println(new PrettyPrintingMap<String, String>(myMap));
注意:您也可以将该逻辑放入实用程序方法中。
Arrays.toString(map.entrySet().toArray())
看看番石榴图书馆:
Joiner.MapJoiner mapJoiner = Joiner.on(",").withKeyValueSeparator("="); System.out.println(mapJoiner.join(map));
Apache库来拯救!
MapUtils.debugPrint(System.out, "myMap", map);
你只需要Apache commons-collections library( 项目链接 )
Maven用户可以使用这个依赖添加库:
<dependency> <groupId>commons-collections</groupId> <artifactId>commons-collections</artifactId> <version>3.2.1</version> </dependency>
当我在类path中有org.json.JSONObject
时,我会这样做:
Map<String, Object> stats = ...; System.out.println(new JSONObject(stats).toString(2));
(这个美丽的缩进列表,集和地图可能是嵌套的)
简单和容易。 欢迎来到JSON世界。 使用Google的Gson :
new Gson().toJson(map)
带3个键的地图示例:
{"array":[null,"Some string"],"just string":"Yo","number":999}
查看OpenJDK源代码中的HashMap#toString()
和AbstractMap#toString()
:
class java.util.HashMap.Entry<K,V> implements Map.Entry<K,V> { public final String toString() { return getKey() + "=" + getValue(); } } class java.util.AbstractMap<K,V> { public String toString() { Iterator<Entry<K,V>> i = entrySet().iterator(); if (! i.hasNext()) return "{}"; StringBuilder sb = new StringBuilder(); sb.append('{'); for (;;) { Entry<K,V> e = i.next(); K key = e.getKey(); V value = e.getValue(); sb.append(key == this ? "(this Map)" : key); sb.append('='); sb.append(value == this ? "(this Map)" : value); if (! i.hasNext()) return sb.append('}').toString(); sb.append(", "); } } }
所以如果来自OpenJDK的人没有find一个更优雅的方式来做到这一点,没有:-)
public void printMapV2 (Map <?, ?> map) { StringBuilder sb = new StringBuilder(128); sb.append("{"); for (Map.Entry<?,?> entry : map.entrySet()) { if (sb.length()>1) { sb.append(", "); } sb.append(entry.getKey()).append("=").append(entry.getValue()); } sb.append("}"); System.out.println(sb); }
我更喜欢将地图转换为JSONstring:
- 一个标准
- 人类可读
- 在Sublime,VS Code等编辑器中支持语法突出显示,格式化和区段隐藏/显示
- 支持JPath,所以编辑器可以准确地报告你已经导航的对象的哪一部分
-
支持对象内嵌套的复杂types
import com.fasterxml.jackson.core.JsonProcessingException; import com.fasterxml.jackson.databind.ObjectMapper; public static String getAsFormattedJsonString(Object object) { ObjectMapper mapper = new ObjectMapper(); try { return mapper.writerWithDefaultPrettyPrinter().writeValueAsString(object); } catch (JsonProcessingException e) { e.printStackTrace(); } return ""; }
你应该可以做你想做的事情:
例如System.out.println(map)
只要地图中的所有对象都覆盖了toString
方法,就会看到:
{key1=value1, key2=value2}
如果这是为你的代码,那么过度toString
是一个很好的习惯,我build议你去代替。
对于你的例子,如果你的对象是String
的话,你应该没问题。
即System.out.println(map)
将打印正是你所需要的,没有任何额外的代码
使用Java 8 Streams:
Map<Object, Object> map = new HashMap<>(); String content = map.entrySet() .stream() .map(e -> e.getKey() + "=\"" + e.getValue() + "\"") .collect(Collectors.joining(", ")); System.out.println(content);
我猜这样的东西会更干净,并为输出格式提供更多的灵活性(只需更改模板):
String template = "%s=\"%s\","; StringBuilder sb = new StringBuilder(); for (Entry e : map.entrySet()) { sb.append(String.format(template, e.getKey(), e.getValue())); } if (sb.length() > 0) { sb.deleteCharAt(sb.length() - 1); // Ugly way to remove the last comma } return sb.toString();
我知道不得不删除最后一个逗号是丑陋的,但我认为它比这个解决scheme之类的替代品更清洁,或手动使用迭代器。
作为利用现有基础架构的快速和肮脏的解决scheme,您可以将uglyPrintedMap
到java.util.HashMap
,然后使用toString()
。
uglyPrintedMap.toString(); // ugly System.out.println( uglyPrintedMap ); // prints in an ugly manner new HashMap<Object, Object>(jobDataMap).toString(); // pretty System.out.println( new HashMap<Object, Object>(uglyPrintedMap) ); // prints in a pretty manner