英文:
Get list of keys in Complex JSON Object (Java 8)
问题
我正在处理一个看起来像这样的JSON:
{
"key1": {
"key1.1": {
"nestedkey1": "something",
"nestedkey2": "something",
"nestedkey3": "Something"
},
"key1.2": {
"nestedkey1": "something",
"nestedkey2": "something",
"nestedkey3": "Something"
}
},
"key2": {
"key2.1": {
"nestedkey1": "something",
"nestedkey2": "something",
"nestedkey3": "Something"
},
"key2.2": {
"nestedkey1": "something",
"nestedkey2": "something",
"nestedkey3": "Something"
}
}
}
我不知道所有的键。我希望获取所有的键,以便我可以创建一个Map<String, Object>
。该映射应该类似于("key1" -> 相应的对象)...
在Java中是否有一种简单的方法来做到这一点?
英文:
I am dealing with a JSON that looks like this :-
{
"key1": {
"key1.1": {
"nestedkey1": "something",
"nestedkey2": "something",
"nestedkey3": "Something"
},
"key1.2": {
"nestedkey1": "something",
"nestedkey2": "something",
"nestedkey3": "Something"
}
},
"key2": {
"key2.1": {
"nestedkey1": "something",
"nestedkey2": "something",
"nestedkey3": "Something"
},
"key2.2": {
"nestedkey1": "something",
"nestedkey2": "something",
"nestedkey3": "Something"
}
}...
And I don't know all the keys. I wish to obtain all the keys so that I can create a Map<String, Object> out of this. That map should look something like ("key1" -> Corresponding object)...
Is there a simple way to do this in Java?
答案1
得分: 2
String filePath = "src/main/resources/json/1.json";
FileReader reader = new FileReader(filePath);
JSONParser parser = new JSONParser();
JSONObject jsonObject = (JSONObject) parser.parse(reader);
Set<String> setKeys = jsonObject.keySet();
Map<String, Object> yourMap = new HashMap<>();
for (String key : setKeys) {
yourMap.put(key, jsonObject.get(key));
}
yourMap is ready!
英文:
String filePath ="src/main/resources/json/1.json";
FileReader reader = new FileReader(filePath);
JSONParser parser = new JSONParser();
JSONObject jsonObject = (JSONObject) parser.parse(reader);
Set<String> setKeys= jsonObject.keySet();
Map<String,Object> yourMap= new HashMap<>();
for (String key:setKeys) {
yourMap.put(key,jsonObject.get(key));
}
yourMap is ready!
答案2
得分: 1
使用Jackson JSON库,这个JSON可以通过TypeReference
解析为Map<String, Object>
:
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import java.util.Map;
public class JsonTest {
public static void main(String[] args) throws JsonProcessingException {
String json = "..."; // JSON字符串,确保JSON有效并且有闭合的 }
ObjectMapper mapper = new ObjectMapper();
Map<String, Object> map = mapper.readValue(json, new TypeReference<>() {});
System.out.println(map);
}
}
要获取所有键的列表,需要实现一个递归方法来迭代顶层映射的条目并添加键:
public static List<String> getKeys(Map<String, Object> map) {
List<String> keys = new ArrayList<>();
for (Map.Entry<String, Object> entry : map.entrySet()) {
keys.add(entry.getKey());
if (entry.getValue() instanceof Map) {
Map<String, Object> nested = (Map<String, Object>) entry.getValue();
keys.addAll(getKeys(nested));
}
}
return keys;
}
类似地,可以创建一个“前缀化”键的列表:
public static List<String> getPrefixedKeys(String prefix, Map<String, Object> map) {
List<String> keys = new ArrayList<>();
for (Map.Entry<String, Object> entry : map.entrySet()) {
String key = prefix + entry.getKey();
keys.add(key);
if (entry.getValue() instanceof Map) {
Map<String, Object> nested = (Map<String, Object>) entry.getValue();
keys.addAll(getPrefixedKeys(key + "/", nested));
}
}
return keys;
}
// 测试
System.out.println(getPrefixedKeys("/", map));
输出:
[/key1, /key1/key1.1, /key1/key1.1/nestedkey1, /key1/key1.1/nestedkey2, /key1/key1.1/nestedkey3,
/key1/key1.2, /key1/key1.2/nestedkey1, /key1/key1.2/nestedkey2, /key1/key1.2/nestedkey3,
/key2, /key2/key2.1, /key2/key2.1/nestedkey1, /key2/key2.1/nestedkey2, /key2/key2.1/nestedkey3,
/key2/key2.2, /key2/key2.2/nestedkey1, /key2/key2.2/nestedkey2, /key2/key2.2/nestedkey3]
英文:
Using Jackson JSON library, this json may be parsed as a Map<String, Object>
using TypeReference
:
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import java.util.Map;
public class JsonTest {
public static void main(String[] args) throws JsonProcessingException {
String json = "{\n"
+ "\"key1\": {\n"
+ " \"key1.1\": {\n"
+ " \"nestedkey1\": \"something\",\n"
+ " \"nestedkey2\": \"something\",\n"
+ " \"nestedkey3\": \"Something\"\n"
+ " },\n"
+ " \"key1.2\": {\n"
+ " \"nestedkey1\": \"something\",\n"
+ " \"nestedkey2\": \"something\",\n"
+ " \"nestedkey3\": \"Something\"\n"
+ " }\n"
+ "},\n"
+ "\"key2\": {\n"
+ " \"key2.1\": {\n"
+ " \"nestedkey1\": \"something\",\n"
+ " \"nestedkey2\": \"something\",\n"
+ " \"nestedkey3\": \"Something\"\n"
+ " },\n"
+ " \"key2.2\": {\n"
+ " \"nestedkey1\": \"something\",\n"
+ " \"nestedkey2\": \"something\",\n"
+ " \"nestedkey3\": \"Something\"\n"
+ " }\n"
+ "}}"; // make sure the json is valid and closing } is available
ObjectMapper mapper = new ObjectMapper();
Map<String, Object> map = mapper.readValue(json, new TypeReference<>() {});
System.out.println(map);
}
}
To get the list of all keys, a recursive method needs to be implemented to iterate over the entries of the top-level map and add keys:
public static List<String> getKeys(Map<String, Object> map) {
List<String> keys = new ArrayList<>();
for (Map.Entry<String, Object> entry : map.entrySet()) {
keys.add(entry.getKey());
if (entry.getValue() instanceof Map) {
Map<String, Object> nested = (Map<String, Object>) entry.getValue();
keys.addAll(getKeys(nested));
}
}
return keys;
}
Similarly, a list of "prefixed" keys may be created:
public static List<String> getPrefixedKeys(String prefix, Map<String, Object> map) {
List<String> keys = new ArrayList<>();
for (Map.Entry<String, Object> entry : map.entrySet()) {
String key = prefix + entry.getKey();
keys.add(key);
if (entry.getValue() instanceof Map) {
Map<String, Object> nested = (Map<String, Object>) entry.getValue();
keys.addAll(getPrefixedKeys(key + "/", nested));
}
}
return keys;
}
// test
System.out.println(getPrefixedKeys("/", map));
Output:
[/key1, /key1/key1.1, /key1/key1.1/nestedkey1, /key1/key1.1/nestedkey2, /key1/key1.1/nestedkey3,
/key1/key1.2, /key1/key1.2/nestedkey1, /key1/key1.2/nestedkey2, /key1/key1.2/nestedkey3,
/key2, /key2/key2.1, /key2/key2.1/nestedkey1, /key2/key2.1/nestedkey2, /key2/key2.1/nestedkey3,
/key2/key2.2, /key2/key2.2/nestedkey1, /key2/key2.2/nestedkey2, /key2/key2.2/nestedkey3]
答案3
得分: 0
计算任务是输出无限级别的JSON记录中所有级别的字段名称。如果您尝试在Java中处理这种情况,代码会变得很长。
在SPL中进行这个操作非常方便,SPL是一个开源的Java包。只需要三行代码就足够了:
A | B | |
---|---|---|
1 | =i=0,json(file("records.json").read()) | |
2 | func recurse(r) | >i+=1,r.fno().run(tmp=eval("r.#"/~),B1=B1.to(:i-1)|r.fname(~),output(B1.concat("->")),if(ifr(tmp),func(recurse,tmp),(B1=B1|tmp))) |
3 | =func(recurse,A1) |
SPL提供了可以被Java调用的JDBC驱动程序。只需将上述SPL脚本存储为jsonkeys.splx,并在Java中调用它,就像调用存储过程一样:
…
Class.forName("com.esproc.jdbc.InternalDriver");
con= DriverManager.getConnection("jdbc:esproc:local://");
st = con.prepareCall("call jsonkeys()");
st.execute();
…
英文:
The computing task is to output field names of all levels in JSON records of indefinite number of levels. The code will be lengthy if you try to handle such a scenario in Java.
It is convenient to do this in SPL, the open-source Java package. Three lines of code are enough:
A | B | |
---|---|---|
1 | =i=0,json(file("records.json").read()) | |
2 | func recurse(r) | >i+=1,r.fno().run(tmp=eval("r.#"/~),B1=B1.to(:i-1)|r.fname(~),output(B1.concat("->")),if(ifr(tmp),func(recurse,tmp),(B1=B1|tmp))) |
3 | =func(recurse,A1) |
SPL offers JDBC driver to be invoked by Java. Just store the above SPL script as jsonkeys.splx and invoke it in Java as you call a stored procedure:
…
Class.forName("com.esproc.jdbc.InternalDriver");
con= DriverManager.getConnection("jdbc:esproc:local://");
st = con.prepareCall("call jsonkeys()");
st.execute();
…
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论