如何解决从JSON到具有动态密钥的JAVA POJO
我正在尝试从JSON转换为JAVA POJO。
我的JSON字符串如下所示:
{
"api": {
"results": 1,"fixtures": [
{
"fixture_id": 38480,"league_id": 95,"lineups": {
"Lecce": {
"coach": "F. Liverani","coach_id": 2442,"formation": "4-2-3-1","startXI": [
{
"team_id": 867,"player_id": 31719,"player": "M. Vigorito","number": 22,"pos": "G"
},{
"team_id": 867,"player_id": 31721,"player": "M. Calderoni","number": 27,"pos": "D"
},"player_id": 31725,"player": "F. Lucioni","number": 25,"pos": "D"
}
],"substitutes": [
{
"team_id": 867,"player_id": 31744,"player": "S. Palombi","number": 14,"pos": "F"
},"player_id": 31740,"player": "A. Tabanelli","number": 23,"player_id": 31739,"player": "M. Scavone","number": 30,"pos": "M"
}
]
},"Spezia": {
"coach": "P. Marino","coach_id": 2899,"startXI": [
{
"team_id": 515,"player_id": 30820,"player": "E. Lamanna","number": 1,{
"team_id": 515,"player_id": 30829,"player": "C. Terzi","number": 19,"player_id": 30824,"player": "E. Capradossi","number": 13,"player_id": 30837,"player": "L. Mora","number": 6,"pos": "M"
}
],"substitutes": [
{
"team_id": 515,"player_id": 30848,"player": "D. Okereke","number": 21,"player_id": 30832,"player": "M. Crimi","number": 15,"pos": "M"
},"player_id": 30842,"player": "S. Bidaoui","number": 26,"pos": "D"
}
]
}
}
}
]
}
}
我的问题是,“ Team”名称是动态的,并且对于我收到的每个匹配夹具JSON字符串都会更改。
我已经使用http://www.jsonschema2pojo.org/来准备文件了,但是看起来像下面这样:
import java.io.Serializable;
import java.util.HashMap;
import java.util.Map;
import org.codehaus.jackson.annotate.JsonAnyGetter;
import org.codehaus.jackson.annotate.JsonAnySetter;
import org.codehaus.jackson.annotate.JsonIgnore;
import org.codehaus.jackson.annotate.JsonProperty;
import org.codehaus.jackson.annotate.JsonPropertyOrder;
import org.codehaus.jackson.map.annotate.JsonSerialize;
@JsonSerialize(include = JsonSerialize.Inclusion.NON_NULL)
@JsonPropertyOrder({
"Lecce","Spezia"
})
public class Lineups implements Serializable
{
@JsonProperty("Lecce")
private Lecce lecce;
@JsonProperty("Spezia")
private Spezia spezia;
@JsonIgnore
private Map<String,Object> additionalProperties = new HashMap<String,Object>();
private final static long serialVersionUID = -2766671198131939159L;
/**
* No args constructor for use in serialization
*
*/
public Lineups() {
}
/**
*
* @param lecce
* @param spezia
*/
public Lineups(Lecce lecce,Spezia spezia) {
super();
this.lecce = lecce;
this.spezia = spezia;
}
@JsonProperty("Lecce")
public Lecce getLecce() {
return lecce;
}
@JsonProperty("Lecce")
public void setLecce(Lecce lecce) {
this.lecce = lecce;
}
@JsonProperty("Spezia")
public Spezia getSpezia() {
return spezia;
}
@JsonProperty("Spezia")
public void setSpezia(Spezia spezia) {
this.spezia = spezia;
}
@JsonAnyGetter
public Map<String,Object> getAdditionalProperties() {
return this.additionalProperties;
}
@JsonAnySetter
public void setAdditionalProperty(String name,Object value) {
this.additionalProperties.put(name,value);
}
}
只要是莱切和斯佩齐亚,它就可以正常工作。如果是其他团队,我将不会获得名称和其他信息。
当我自己进行映射时,我已经成功地以另一种方式解决了这个问题。 然后我像这样解决了它:
public static class Lineups {
private Map<String,Team> team = new LinkedHashMap<>();
public Map<String,Team> getTeam() {
return team;
}
public void setTeam(Map<String,Team> team) {
this.team = team;
}
@JsonAnySetter
public void setTeam(String key,Team value) {
this.team.put(key,value);
}
public Lineups() {
}
}
但是我想组织它并使用注释,因为我在较早的设置中收到的JSON文件还有其他问题。
我尝试在新设置中使用与Map
有没有人可以帮助我解决该问题并使它与我从http://www.jsonschema2pojo.org/获得的文件一起使用。
解决方法
从顶部讲:
第一部分是一个对象,其字段名为api
:
{
"api": {
class Root {
@JsonProperty("api") private API api;
}
下一部分是一个对象,该对象具有两个名为results
和fixtures
的字段,其中fixtures
是数组或List
,我们通常更喜欢使用{{1} }:
List
"results": 1,"fixtures": [
下一部分是一个具有三个字段的对象,分别名为class API {
@JsonProperty("results") private int results;
@JsonProperty("fixtures") private List<Fixture> fixtures; // array
}
,fixture_id
和league_id
,其中lineups
是associative array,在Java中是lineups
:
Map<String,?>
{
"fixture_id": 38480,"league_id": 95,"lineups": {
"Lecce": {
其余的很简单:
class Fixture {
@JsonProperty("fixture_id") private int fixtureId;
@JsonProperty("league_id") private int leagueId;
@JsonProperty("lineups") private Map<String,Lineup> lineups; // associative array
}
"coach": "F. Liverani","coach_id": 2442,"formation": "4-2-3-1","startXI": [
...
],"substitutes": [
...
]
class Lineup {
@JsonProperty("coach") private String coach;
@JsonProperty("coach_id") private int coachId;
@JsonProperty("formation") private String formation;
@JsonProperty("startXI") private List<Player> startXI;
@JsonProperty("substitutes") private List<Player> substitutes;
}
{
"team_id": 867,"player_id": 31719,"player": "M. Vigorito","number": 22,"pos": "G"
},
,
我通常会真正进入代码注释(代码文档),但是使用诸如 JSON解析之类的代码时,代码行是如此自成一体不言而喻,这似乎没有必要。我正在练习使用 JSON库 javax.json
...
我不使用Java的组件注释(以前称为 Java Beans ),因此按常规方式编写constructors
和getters
是我习惯了。
这是我的版本...比其他版本长,但是易读性和添加/删除方法非常简单。
import java.io.*;
import javax.json.*;
import java.util.*;
public class S
{
public static class Player
{
public final String name,position;
public final int playerId,teamId,number;
public final boolean starting;
public Player(String name,String position,int playerId,int teamId,int number,boolean starting)
{
this.name=name; this.position=position;
this.playerId=playerId; this.teamId=teamId; this.number=number;
this.starting=starting;
}
public String toString()
{
return
"Name: " + name + '\n' +
"Position: " + position + '\n' +
"Number: " + number + '\n' +
"Starting: " + (starting ? "Starting Lineup" : "Substitute") + '\n';
}
}
public static class Team extends Vector<Player>
{
public final String teamName,coachName,formation;
public final int coachId;
public Team(String teamName,String coachName,int coachId,String formation)
{
this.teamName=teamName; this.coachName=coachName; this.coachId=coachId;
this.formation=formation;
}
public Player findByName(String name)
{
for (Player player : this) if (player.name.equalsIgnoreCase(name)) return player;
return null;
}
public Player findByNumber(int number)
{
for (Player player : this) if (player.number == number) return player;
return null;
}
public Player findByPosition(String position)
{
for (Player player : this) if (player.position.equalsIgnoreCase(position)) return player;
return null;
}
public String toString()
{
StringBuffer sb = new StringBuffer();
sb.append(
"Team Name: " + teamName + '\n' +
"Coach Name: " + coachName + '\n' +
"Formation: " + formation + "\n\n"
);
for (Player player : this) sb.append(player.toString() + "\n");
return sb.toString();
}
}
public static void main(String[] argv) throws IOException
{
Reader r = new FileReader("teams.json");
JsonObject teamsList = Json
.createReader(r)
.readObject()
.getJsonObject("api")
.getJsonArray("fixtures")
.getJsonObject(0)
.getJsonObject("lineups");
Vector<Team> teams = new Vector<>();
for (String teamName : teamsList.keySet())
{
JsonObject teamObj = teamsList.getJsonObject(teamName);
String coachName = teamObj.getString("coach");
int coachId = teamObj.getInt("coach_id");
String formation = teamObj.getString("formation");
JsonArray startingLineup = teamObj.getJsonArray("startXI");
JsonArray substitutes = teamObj.getJsonArray("substitutes");
List<JsonArray> lineups = new Vector<>();
Team team = new Team(teamName,coachId,formation);
int count = 0;
teams.add(team);
lineups.add(startingLineup);
lineups.add(substitutes);
for (JsonArray lineup : lineups)
{
boolean starting = (count++ == 0);
for (JsonObject playerObj : lineup.getValuesAs(JsonObject.class))
{
int teamId = playerObj.getInt("team_id");
int playerId = playerObj.getInt("player_id");
String name = playerObj.getString("player");
int number = playerObj.getInt("number");
String position = playerObj.getString("pos");
Player player = new Player(name,position,playerId,number,starting);
team.add(player);
}
}
}
for (Team team : teams) System.out.println(team.toString() + "\n");
}
}
此代码将产生以下输出:
Team Name: Lecce
Coach Name: F. Liverani
Formation: 4-2-3-1
Name: M. Vigorito
Position: G
Number: 22
Starting: Starting Lineup
Name: M. Calderoni
Position: D
Number: 27
Starting: Starting Lineup
Name: F. Lucioni
Position: D
Number: 25
Starting: Starting Lineup
Name: S. Palombi
Position: F
Number: 14
Starting: Substitute
Name: A. Tabanelli
Position: D
Number: 23
Starting: Substitute
Name: M. Scavone
Position: M
Number: 30
Starting: Substitute
Team Name: Spezia
Coach Name: P. Marino
Formation: 4-2-3-1
Name: E. Lamanna
Position: G
Number: 1
Starting: Starting Lineup
Name: C. Terzi
Position: D
Number: 19
Starting: Starting Lineup
Name: E. Capradossi
Position: D
Number: 13
Starting: Starting Lineup
Name: L. Mora
Position: M
Number: 6
Starting: Starting Lineup
Name: D. Okereke
Position: G
Number: 21
Starting: Substitute
Name: M. Crimi
Position: M
Number: 15
Starting: Substitute
Name: S. Bidaoui
Position: D
Number: 26
Starting: Substitute
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。