我很好奇如何在Java中更有效地实例化字典。目前我有可通过的代码,但我以非常模糊的方式填充数据。
有没有办法让我初始化我的字典?这是记录的python:
westernCanadaAdjList = { 'BC': ['AB'],
'AB': ['BC', 'SK'],
'SK': ['AB', 'MB'],
'MB': ['SK']
}
我发现用于演示的目的更加清晰。
我目前在Java中的代码:
public class Main {
public static void main(String[] args) {
//Adjacency List representation through a dictionary. Allows fast O(1) lookup time.
Map<String,ArrayList<String>> adjList = new HashMap<String,ArrayList<String>>();
//Adding values for Edmonton
adjList.put("Edmonton", new ArrayList<String>());
adjList.get("Edmonton").add("Neighbour1");
adjList.get("Edmonton").add("Neighbour2");
adjList.get("Edmonton").add("Neighbour3");
//Adding values for Vancouver
adjList.put("Vancouver", new ArrayList<String>());
adjList.get("Vancouver").add("V neighbour1");
adjList.get("Vancouver").add("V neighbour2");
System.out.println(adjList.keySet() +" And Values " + adjList.values());
for (String neighbour: adjList.get("Edmonton")){
System.out.println(neighbour);
}
for (String neighbour: adjList.get("Vancouver")){
System.out.println(neighbour);
}
}
}
非常感谢!
答案 0 :(得分:6)
这是我所知道的最好的技术:
Map<String, String> myMap = new HashMap<String, String>() {{
put("foo", "bar");
put("key", "value");
//etc
}};
请注意双括号 - 这通常称为双括号初始化。
你真正在做的是创建一个扩展HashMap的匿名内部类,你的新子类包含一个初始化块,你可以在其中调用任何保证在使用实例之前执行的任意代码。 / p>
另请注意,无论出于何种原因,'diamond operator'都不能与匿名类一起使用。
对于测试类来说,这是一种很好的技术,但我倾向于将其用于生产代码。
编辑:我想我应该回答你的实际问题!
双支撑初始化可能是“纯”Java中的最佳解决方案,您的Map将具体看起来像:
Map<String, List<String>> westernCanadaAdjList = new HashMap<String, List<String>> () {{
put("BC", new ArrayList<String>(){{ add("AB"); }});
put("AB", new ArrayList<String>(){{ add("BC"); add("SK"); }});
put("SK", new ArrayList<String>(){{ add("AB"); add("MB"); }});
put("MB", new ArrayList<String>(){{ add("SK"); }});
}};
......仍然不是超级棒。 Java确实需要一个Map文字,而且它没有。
对于生产代码,我会使用Guava的MultiMap,但老实说用文字填充它并不是更好:
Multimap<String, String> multimap = ArrayListMultimap.create();
multimap.put("BC", "AB");
multimap.put("AB", "BC");
multimap.put("AB", "SK");
multimap.put("SK", "SK");
multimap.put("SK", "SK");
multimap.put("SK", "SK");
答案 1 :(得分:2)
是的,您可以:将其解析为json:
import com.fasterxml.jackson.databind.ObjectMapper;
String json = "{'BC': ['AB']," +
"'AB': ['BC', 'SK']," +
"'SK': ['AB', 'MB']," +
"'MB': ['SK']"
"}";
Map<String, Object> map = new ObjectMapper().readValue(json, HashMap.class);
答案 2 :(得分:1)
我同意路易斯并且不打算添加任何东西。
在这种情况下使用流可以让你将代码压缩成一行,但我意识到这不是你问题的答案(只是我能想到的最接近)。
Map<String, List<String>> adjList = Stream.of(
new SimpleEntry<>("Edmonton", Arrays.asList("E N1", "E N2", "E N3")),
new SimpleEntry<>("Vancouver", Arrays.asList("V N1", "V N2", "V N3")))
.collect(Collectors.toMap((e) -> e.getKey(), (e) -> e.getValue()));
答案 3 :(得分:1)
我最近遇到了类似的问题。我将数据表示为2d数组,相对容易键入和解析,并编写了一个实用程序方法来将其解析为数据结构。例如为你的情况
static String[][] CANADA_DATA = {
{"BC"," AB"},
{"AB","BC","SK"},
// rest of Canada here
}
示例代码
public Map<String, List<String>> parseIt() {
Map<String, List<String>> map = new HashMap();
for (String[] provinceData : CANADA_DATA ) {
String name = provinceData [0];
ArrayList neighbors = new ArrayList(Arrays.asList(provinceData ));
neighbors.remove(0); // remove ourself
map.put(name, neighbors);
}
return map;
}
显然,您可以更改数据格式并解析代码以满足您的特定需求。