在Java中,我需要使用一系列任意密钥消费JSON(下图(,并产生Map<String, String>
。我想使用标准,长期支持的JSON库进行解析。但是,我的研究表明,这些图书馆是为Java课程的避难所设置的设置,您可以提前知道字段。我只需要构建地图。
实际上比这更复杂的一步,因为任意密钥不是JSON的最高级别。它们仅作为prefs
的子对象出现。其余的是已知的,并且可以适合预定的类。
{
"al" : { "type": "admin", "prefs" : { "arbitrary_key_a":"arbitary_value_a", "arbitrary_key_b":"arbitary_value_b"}},
"bert" : {"type": "user", "prefs" : { "arbitrary_key_x":"arbitary_value_x", "arbitrary_key_y":"arbitary_value_y"}},
...
}
在Java中,我希望能够拿起该字符串,然后做类似的事情:
people.get("al").get("prefs"); // Returns Map<String, String>
我该怎么做?我想使用标准的良好支持的解析器,避免例外,并保持简单。
更新
@kumensa指出,这比看起来要难。能够做:
people.get("al").getPrefs(); // Returns Map<String, String>
people.get("al").getType(); // Returns String
也一样好。
应该将JSON解析为:
public class Person {
public String type;
public HashMap<String, String> prefs;
}
// JSON parsed to:
HashMap<String, Person>
拥有您的Person
类并使用GSON,您可以简单地做:
final Map<String, Person> result = new Gson().fromJson(json, new TypeToken<Map<String, Person>>() {}.getType());
然后,通过people.get("al").getPrefs();
来检索prefs
。
但要小心:您的JSON字符串无效。它不应从"people:"
开始。
public static <T> Map<String, T> readMap(String json) {
if (StringUtils.isEmpty(json))
return Collections.emptyMap();
ObjectReader reader = new ObjectMapper().readerFor(Map.class);
MappingIterator<Map<String, T>> it = reader.readValues(json);
if (it.hasNextValue()) {
Map<String, T> res = it.next();
return res.isEmpty() ? Collections.emptyMap() : res;
}
return Collections.emptyMap();
}
您下一步需要做的一切,它检查Object
的类型。如果是Map
,则您有一个对象。否则,这是一个简单的值。
您可以使用Jackson Lib实现这一目标。将以下内容放入pom.xml。
中<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.9.8</version>
</dependency>
请参阅以下片段,显示相同的内容。
ObjectMapper mapper = new ObjectMapper();
HashMap<String, Object> people = mapper.readValue(jsonString, new TypeReference<HashMap>(){});
现在,它被视为地图;
完整示例:
import java.io.IOException;
import java.util.HashMap;
import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.ObjectMapper;
public class testMain {
public static void main(String[] args) throws JsonParseException, JsonMappingException, IOException {
String json = "{"address":"3, 43, Cashier Layout, Tavarekere Main Road, 1st Stage, BTM Layout, Ambika Medical, 560029","addressparts":{"apartment":"Cashier Layout","area":"BTM Layout","floor":"3","house":"43","landmark":"Ambika Medical","pincode":"560029","street":"Tavarekere Main Road","subarea":"1st Stage"}}";
ObjectMapper mapper = new ObjectMapper();
HashMap<String, Object> people = mapper.readValue(json, new TypeReference<HashMap>(){});
System.out.println(((HashMap<String, String>)people.get("addressparts")).get("apartment"));
}
}
输出:收银员布局