考虑以下RealmObject子类
public class TimeSlot extends RealmObject
{
@PrimaryKey
private int value = 0;
private int hits = 0;
@LinkingObjects("ats") private final RealmResults<Visit> visits = null;
public TimeSlot(){}
public TimeSlot(int time)
{
super();
value = time;
}
...
}
public class Visit extends RealmObject
{
private RealmList<TimeSlot> timeslots = null;
public Visit()
{
super();
timeslots = new RealmList<TimeSlot>();
}
public void addTimeSlot(TimeSlot ts) throws Exception
{
this.timeslots.add(ts);
try
{
myRealm.beginTransaction();
myRealm.copyToRealmOrUpdate(this,ImportFlag.valueOf("CheckSameValuesBeforeSet"));
myRealm.commitTransaction();
}
catch(Exception e)
{
myRealm.cancelTransaction();
throw e;
}
}
}
我在代码的其他地方执行以下操作
myVisit.addTimeSlot(new TimeSlot(30));
向访问对象
TimeSlot
的现有实例添加新的myVisit
。您会注意到,在addTimeSlot
中,我将修改后的Visit
实例复制到Realm。我的问题-这样做还会保留新创建的TimeSlot对象吗?一个相关的问题-当我从Realm中检索myVisit时,是否可以保证myVisit.timeslots中的TimeSlot对象与添加它们时的顺序相同?
最佳答案
如果您知道在哪里查看,大多数问题都会在Realm文档中回答。主要文档中提示了许多这些问题,然后您需要找到正确的API页面。有时只能尝试一下。
您会注意到,在addTimeSlot中,我将修改后的Visit实例复制到Realm。我的问题-这样做还会保留新创建的TimeSlot对象吗?
那是对的。 copyToRealmOrUpdate的文档状态:“这是深层副本或更新,即所有引用的对象都将被复制或更新。”
您已经介绍了一个潜在的问题。 addTimeSlot
的第一行立即修改Visit
对象。如果Visit
对象不受管理,或者在addTimeSlot
调用之外启动了Realm事务,这很好。但是,如果不是这种情况,那么您将收到有关“尝试在写事务之外修改对象”的异常。您的方法依赖于您始终对对象的非托管版本进行操作,并将每个更改手动复制回Realm。实际上,这不是推荐的方法,因为这可能会导致对象不同步。始终处理托管对象更好。
您还正在访问一个名为myRealm
的变量,我认为该变量是对您的Realm的全局引用。请注意,对于托管对象,可以访问getRealm()
函数以检索对象的领域,并避免使用全局变量/传递参数。
因此,最好是:
创建Visit
时将其添加到领域
在addTimeSlot
中,使用getRealm()
的结果验证是否管理了Visit
。如果是这样,请将TimeSlot
添加到Realm和RealmList。
我对您的TimeSlot
主键的工作方式感兴趣。
无论如何,回到您的问题。
当我从Realm检索myVisit时,是否可以保证myVisit.timeslots中的TimeSlot对象与添加它们时的顺序相同?
是。 RealmList
已订购。您可以将元素添加到末尾,也可以通过添加RealmList
来添加。如果未存储订单,这显然是多余的。请参见the docs。
文档提到非托管对象就像简单的POJO。据我了解,如果我创建RealObject子类实例并且从不费心将其复制到Realm,它将保持“不受管”状态。
正确。
但是,如果我将其添加到作为“托管” RealmObject一部分的RealmList实例中会发生什么?
在here中讨论。然后,您的列表就是一个托管领域列表,该语句适用:
可以将非托管对象添加到已托管的RealmList中。在这种情况下,如果对象具有主键,则将使用Realm.copyToRealm(RealmModel,ImportFlag ...)或Realm.copyToRealmOrUpdate(RealmModel,ImportFlag ...)将对象透明地复制到Realm。
请注意,尽管您对对象的现有引用是对象的非托管版本,所以请当心。更改其字段不会更改托管版本。此时,最好放弃您的非托管版本,而仅处理托管对象。
我明白你为什么感到困惑。希望对您有所帮助。
关于java - 如何持久保存引用的RealmObjects,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/59693019/