Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/379.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 如何使用领域创建递归关系?_Java_Android_Realm - Fatal编程技术网

Java 如何使用领域创建递归关系?

Java 如何使用领域创建递归关系?,java,android,realm,Java,Android,Realm,型号: 活动: public class Dog extends RealmObject { @PrimaryKey public String id = UUID.randomUUID().toString(); ... other random String attributes public Dog mother; } 当我运行此代码时,它给了我以下错误: 属于其他线程中的领域实例的对象无法复制到此领域实例。 我让它工作的唯一方法是使用realm.copyFromReal

型号:

活动:

public class Dog extends RealmObject {
  @PrimaryKey
  public String id = UUID.randomUUID().toString();
  ... other random String attributes
  public Dog mother;
}
当我运行此代码时,它给了我以下错误:

属于其他线程中的领域实例的对象无法复制到此领域实例。

我让它工作的唯一方法是使用realm.copyFromRealm(),但整个对象都被复制了,我不希望这样

我是否应该单独保存母亲Id,然后在我的应用程序中查询母亲,无论我在哪里需要它

有没有一种方法可以在不复制整个对象的情况下实现我想要做的事情


编辑:

我最初认为整个对象是使用realm.copyFromRealm()复制的,因为它在realm browser中的外观。
我刚刚测试了更新dog.mother中的一个字段,它更新了链接对象,这意味着它不是副本。

我仍然不知道这是实现我想要做的事情的最佳方式还是正确方式,但它实现了我想要的。

发生异常是因为您在UI线程上构造了
Dog
对象,然后将其传递给异步工作线程,但这意味着您还将引用传递给了
母亲
,这是不允许的。相反,您需要在异步方法中执行如下设置:

public class CustomActivity extends AppCompatActivity {
  private Realm realm;
  private Dog dog = new Dog();

  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    ...
    realm = Realm.getDefaultInstance();
  }

  @Override
  public void onDestroy() {
    super.onDestroy();
    realm.close();
  }

  private void setMother(int id) {
   dog.mother = realm.where(Dog.class).equalTo(ID, id).findFirst();
  }

  private void saveDog() {
   realm.executeTransactionAsync(new Realm.Transaction() {
      @Override
      public void execute(Realm realm) {
        realm.copyToRealmOrUpdate(dog);
      }
    });
  }

}

发生异常是因为您在UI线程上构造了
Dog
对象,然后将其传递给异步工作线程,但这意味着您还将引用传递给了
母线程,这是不允许的。相反,您需要在异步方法中执行如下设置:

public class CustomActivity extends AppCompatActivity {
  private Realm realm;
  private Dog dog = new Dog();

  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    ...
    realm = Realm.getDefaultInstance();
  }

  @Override
  public void onDestroy() {
    super.onDestroy();
    realm.close();
  }

  private void setMother(int id) {
   dog.mother = realm.where(Dog.class).equalTo(ID, id).findFirst();
  }

  private void saveDog() {
   realm.executeTransactionAsync(new Realm.Transaction() {
      @Override
      public void execute(Realm realm) {
        realm.copyToRealmOrUpdate(dog);
      }
    });
  }

}

这个问题的答案将取决于母亲是否已经在王国中,以及您希望它如何更新。您只需创建图形的完整内存表示,然后对所有图形执行
copyToRealmOrUpdate
,但这可能不是您想要的。母图形将始终首先在域中。很抱歉,我不太明白您所说的“创建图形的完整内存表示并执行copyToRealmOrUpdate”是什么意思。在我的例子中我所做的不是吗?我的最终目标是创建一个链接,只需获得对母亲的引用即可。我现在这样做:
dog.mother=realm.copyFromRealm(realm.where(dog.class).equalTo(ID,ID.findFirst())这样做可以吗?这个问题的答案将取决于母亲是否已经在域中,以及您希望它如何更新。您只需创建图形的完整内存表示,然后对所有图形执行
copyToRealmOrUpdate
,但这可能不是您想要的。母图形将始终首先在域中。很抱歉,我不太明白您所说的“创建图形的完整内存表示并执行copyToRealmOrUpdate”是什么意思。在我的例子中我所做的不是吗?我的最终目标是创建一个链接,只需获得对母亲的引用即可。我现在这样做:
dog.mother=realm.copyFromRealm(realm.where(dog.class).equalTo(ID,ID.findFirst())这样做可以吗?谢谢你的回答,它真的帮助我了解我的错误是什么。还有一件事,假设我想显示一些母亲属性的预览,直到用户按下保存按钮。我应该用copyFromRealm查询母亲一次并将其链接到我的新狗,还是在我想显示它的地方查询母亲(不将其链接到新狗),然后在用户决定保存时进行第二次查询?这里的最佳做法是什么?
查询我想在哪里显示它的母亲(不将其与新狗链接),然后在用户决定保存时进行第二次查询?
听起来不错谢谢您的回答,它确实帮助我了解我的错误。还有一件事,假设我想显示一些母亲属性的预览,直到用户按下保存按钮。我应该用copyFromRealm查询母亲一次并将其链接到我的新狗,还是在我想显示它的地方查询母亲(不将其链接到新狗),然后在用户决定保存时进行第二次查询?这里的最佳做法是什么?
查询我想在哪里显示它的母亲(不将它与新狗链接),然后在用户决定保存时进行第二次查询?
听起来不错
  private Realm realm;    

  @Override
  protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    ...
    realm = Realm.getDefaultInstance(); //<--- this is on ui thread
realm.executeTransactionAsync(new Realm.Transaction() {
  @Override
  public void execute(Realm realm) {
    realm.copyToRealmOrUpdate(dog);  // <-- this is on background thread
  //...


private void setMother(int id) {
   dog.mother = realm.where(Dog.class).equalTo(ID, id).findFirst(); // <-- uses UI-thread Realm stored as field
  private void setMother(Realm realm, Dog dog, int id) {
   dog.mother = realm.where(Dog.class).equalTo(ID, id).findFirst();
  }

  private void saveDog() {
   realm.executeTransactionAsync(new Realm.Transaction() {
      @Override
      public void execute(Realm realm) {
        Dog _dog = realm.copyToRealmOrUpdate(dog);
        setMother(realm, _dog, id);
      }
    });