Java 使用jackson转换带有重复密钥的JSON
我正在将json转换为java对象,但我没有得到我想要的。 我在json中复制了密钥“friend” 我的json:Java 使用jackson转换带有重复密钥的JSON,java,json,jackson,jackson-databind,Java,Json,Jackson,Jackson Databind,我正在将json转换为java对象,但我没有得到我想要的。 我在json中复制了密钥“friend” 我的json: { "id" : "5ee2e2f780bc8e7511a65de9", "friends": [{ "friend": { "id": 1, "name": "Priscilla Lynch" }, "friend": { "id": 2,
{
"id" : "5ee2e2f780bc8e7511a65de9",
"friends": [{
"friend": {
"id": 1,
"name": "Priscilla Lynch"
},
"friend": {
"id": 2,
"name": "William Lawrence"
}
}]
}
从ObjectMapper使用readValue只需要最后一个“朋友”,但我需要这两个。
我知道JSONObject使用Map进行转换,所以它使用最后一个
结果:
联系人(id=5ee2e2f780bc8e7511a65de9,friends=[{friend={id=2,name=William Lawrence}}}])
联系Pojo:
@Getter
@Setter
@ToString
public class Contacts {
String id;
List<Object> friends;
}
@Getter
@塞特
@托斯特林
公共类联系人{
字符串id;
列出朋友;
}
我要一份所有朋友的名单。由于提供json的服务不在我手中,我需要找到一种解决方法。
我尝试使用apache.commons中的MultiMap,但没有成功。
我对此一窍不通。也创建“Friend”的POJO类,然后像这样编辑“Contacts”类
public class Contacts {
String id;
List<Friend> friends;
}
公共类联系人{
字符串id;
列出朋友;
}
然后,当您有一个带有重复字段的
JSON对象时,您应该可以使用com.fasterxml.jackson.annotation.JsonAnySetter
annotation来获得好友项列表。结果将是一个列表
,因此,您可以使用flatMap
方法创建List
。请参见以下示例:
import com.fasterxml.jackson.annotation.JsonAnySetter;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.json.JsonMapper;
import lombok.Getter;
import lombok.Setter;
import lombok.ToString;
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;
public class DuplicatedFieldsInJsonObjectApp {
public static void main(String[] args) throws Exception {
File jsonFile = new File("./resource/test.json").getAbsoluteFile();
ObjectMapper mapper = JsonMapper.builder().build();
Contacts contacts = mapper.readValue(jsonFile, Contacts.class);
System.out.println(contacts.getUnwrappedFriends());
}
}
@Getter
@Setter
@ToString
class Contacts {
String id;
List<Friends> friends;
public List<Friend> getUnwrappedFriends() {
return friends.stream().flatMap(f -> f.getFriends().stream()).collect(Collectors.toList());
}
}
class Friends {
private List<Friend> friends = new ArrayList<>();
@JsonAnySetter
public void setAny(String property, Friend friend) {
friends.add(friend);
}
public List<Friend> getFriends() {
return friends;
}
}
@Getter
@Setter
@ToString
class Friend {
int id;
String name;
}
你需要Friend
作为对象吗?因为你可以从JsonNode
中提取它们,而无需对它们进行反序列化。是的,我需要一个朋友列表。你的json有点奇怪。在同一节点中有两个同名的字段friend
。这使得杰克逊只能选择其中一个(最后一个)。因此,即使您使用JsonNode处理它,第一个friend
也会丢失。您可以执行这个JsonNode JsonNode=mapper.readTree(json);System.out.println(jsonNode.get(“friends”).get(0.toString())
它打印数组的第一个元素friends
。它只打印了一个,而不是两个。在我看来,json是“错误的”。您的朋友
是这样的[{{},{}}]
@KunLun,JSON
负载是有效的。对象结构表示为围绕零个或多个名称/值对的一对花括号标记。名称是一个字符串。每个名称后面都有一个冒号标记,将名称与值分开。单个逗号标记将值与以下名称分隔开。JSON语法不对用作名称的字符串施加任何限制,不要求名称字符串是唯一的,也不为名称/值对的顺序分配任何意义。您错过了friends
是一个包含单个对象的数组:friends[{{{friend},{friend}}]
。我尝试了这种方法,但我发现我的@JsonAnySetter
注释方法在我Sys.out
时没有得到重复的条目。我的意思是,当我在@jsonanyster
带注释的方法中打印键
和值
时,即使是重复的键
和最后一个值,我也只能看到一个条目。这就好像Jackson
在使用此方法之前已经忽略了重复的条目。我已经把我的问题贴在这里了。一个机会,请让我知道我该怎么做。
import com.fasterxml.jackson.annotation.JsonAnySetter;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.json.JsonMapper;
import lombok.Getter;
import lombok.Setter;
import lombok.ToString;
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;
public class DuplicatedFieldsInJsonObjectApp {
public static void main(String[] args) throws Exception {
File jsonFile = new File("./resource/test.json").getAbsoluteFile();
ObjectMapper mapper = JsonMapper.builder().build();
Contacts contacts = mapper.readValue(jsonFile, Contacts.class);
System.out.println(contacts.getUnwrappedFriends());
}
}
@Getter
@Setter
@ToString
class Contacts {
String id;
List<Friends> friends;
public List<Friend> getUnwrappedFriends() {
return friends.stream().flatMap(f -> f.getFriends().stream()).collect(Collectors.toList());
}
}
class Friends {
private List<Friend> friends = new ArrayList<>();
@JsonAnySetter
public void setAny(String property, Friend friend) {
friends.add(friend);
}
public List<Friend> getFriends() {
return friends;
}
}
@Getter
@Setter
@ToString
class Friend {
int id;
String name;
}
[Friend(id=1, name=Priscilla Lynch), Friend(id=2, name=William Lawrence)]