当前位置: 首页 > 知识库问答 >
问题:

删除双向递归关系的最简单方法是什么?

阚允晨
2023-03-14

我使用Gson库将Java对象转换成Json响应...问题是,在JPA请求之后,从DB检索的对象不能被转换,因为与其他实体存在递归关系(参见我之前的问题),例如:

public class Gps implements Serializable {
    private static final long serialVersionUID = 1L;
    @Id
    @Basic(optional = false)
    @Column(name = "IMEI", nullable = false, length = 20)
    private String imei;
    //some code here...
    @OneToMany(cascade = CascadeType.ALL, mappedBy = "gpsImei", fetch = FetchType.LAZY)
    private List<Coordonnees> coordonneesList;


public class Coordonnees implements Serializable {
    private static final long serialVersionUID = 1L;
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Basic(optional = false)
    @Column(name = "IDCOORDONNEES", nullable = false)
    private Integer idcoordonnees;
    //some code here...
    @JoinColumn(name = "GPS_IMEI", referencedColumnName = "IMEI", nullable = false)
    @ManyToOne(optional = false, fetch = FetchType.LAZY)
    private Gps gpsImei;

我的源代码:

  EntityManagerFactory emf=Persistence.createEntityManagerFactory("JavaApplication21PU");
  GpsJpaController gjc=new GpsJpaController(emf);

  Gps gps=gjc.findGps("123456789012345");

  for(int i=0;i<gps.getCoordonneesList().size();i++){
   gps.getCoordonneesList().get(i).setGpsImei(null);
  }  

  Gson gson=new Gson();
  String json=gson.toJson(gps);//convert to json response

  System.out.println(json);  

正如你在这里看到的,我做了:

   for(int i=0;i<gps.getCoordonneesList().size();i++){
     gps.getCoordonneesList().get(i).setGpsImei(null);
   }  

只有通过为coordonneesList中的每个GPS对象设置null来杀死递归关系。

你认为这是一个好的解决办法,还是有其他更实用的方法?谢谢

共有3个答案

郑西岭
2023-03-14

我会将 GsonBuilder 配置为使用 jackson 注释:

GsonBuilder builder = new GsonBuilder()
    .addSerializationExclusionStrategy(serializationExclusionStrategy);

final ExclusionStrategy serializationExclusionStrategy = new ExclusionStrategy() {
  @Override
  public boolean shouldSkipField(FieldAttributes f) {
    return f.getAnnotation(JsonIgnore.class) != null
           || f.getAnnotation(JsonBackReference.class) != null;
  }

  @Override
  public boolean shouldSkipClass(Class<?> aClass) {
    return false;
  }
};
韦昊焜
2023-03-14

我不知道Gson,但我正在和Jackson合作。查找使用其 ObjectMapper 类的示例。至于递归,使用 @JsonManagedReference 和 @JsonBackReference 来阻止它。也查找这些示例用法。

万俟小林
2023-03-14

有一个名为 GraphAdapterBuilder 的 Gson 扩展,它可以序列化包含循环引用的对象。下面是相应测试用例中一个非常简化的示例:

Roshambo rock = new Roshambo("ROCK");
Roshambo scissors = new Roshambo("SCISSORS");
Roshambo paper = new Roshambo("PAPER");
rock.beats = scissors;
scissors.beats = paper;
paper.beats = rock;

GsonBuilder gsonBuilder = new GsonBuilder();
new GraphAdapterBuilder()
    .addType(Roshambo.class)
    .registerOn(gsonBuilder);
Gson gson = gsonBuilder.create();
System.out.println(gson.toJson(rock));

这将打印:

{
  '0x1': {'name': 'ROCK', 'beats': '0x2'},
  '0x2': {'name': 'SCISSORS', 'beats': '0x3'},
  '0x3': {'name': 'PAPER', 'beats': '0x1'}
}

请注意,GraphAdapterBuilder 类不包含在 gson.jar 中。如果要使用它,则必须手动将其复制到项目中。

 类似资料:
  • 问题内容: 我使用Gson 库将Java对象转换为Json响应…问题是,在JPA请求之后,由于与其他实体的递归关系,无法转换从DB检索到的对象: 我的源代码: 如您在这里看到的,我做了: 只是通过为coordonneesList中的每个GPS对象设置null来消除递归关系。 您认为这是一个很好的解决方案,或者还有其他更实用的方法吗?谢谢 问题答案: 有一个名为GraphAdapterBuilder

  • 首先,这是我的实体。 玩家: 团队: 正如已经说明的许多主题一样,您可以通过Jackson以多种方式避免WebService中的StackOverflow Exeption。 这很酷,除了JPA之外,在序列化之前,所有的实体都可以无限递归地构造另一个实体。这只是丑陋的ans请求需要更长的时间。检查这个截图:IntelliJ调试器 有办法解决吗?知道我希望根据endpoint获得不同的结果。示例:

  • 问题内容: 我目前正在尝试递归删除目录…奇怪的是,我能够找到的最短代码是以下结构,采用了一个 临时内部类 并且采用了 访问者模式 … 资料来源:这里 鉴于新的API消除了太多的混乱和样板,这让人感到非常笨拙和冗长。 有没有更短的方法可以实现强制递归目录删除? 我正在寻找纯本地Java 1.8方法,所以请不要链接到外部库… 问题答案: 您可以结合使用NIO 2和Stream API。 -返回以下所有

  • 我正在寻找如何删除关系的寄存器一对多/多对一。问题是当我执行EntityManager.remove()时,所有记录都被删除,我希望删除唯一的孩子(DiasTurma)而不是您的父级(Turma)。 我是这样尝试的 方法

  • 问题内容: 在SQL Server中进行递归自联接的最简单方法是什么?我有一个这样的表: 而且我希望能够获取仅与特定人员开始的层次结构相关的记录。因此,如果我通过PersonID = 1请求CJ的层次结构,则会得到: 对于EB,我会得到: 除了基于一堆连接的固定深度响应之外,我对此深感困惑。之所以会这样,是因为我们没有很多级别,但我想正确地做到这一点。 谢谢!克里斯。 问题答案: 通过添加排序条件

  • 问题内容: 我正在尝试修复我的virtualenv之一-我想将所有已安装的库重置为与生产相匹配的库。 有没有一种快速简便的方法来使用pip? 问题答案: 我已找到此代码段作为替代解决方案。与重建virtualenv相比,这是对库的更优雅的删除: 如果您通过VCS安装了软件包,则需要排除这些行并手动删除软件包(从下面的注释中升高):