【发布时间】:2026-01-20 06:35:01
【问题描述】:
我正在尝试启动并运行 Android 开发和 Room。
我正在制作一个带有播放列表和文件浏览器的音乐播放器应用程序,它能够将曲目添加到当前播放列表中。
我将播放列表保存在 Room 数据库中。
我在第一次运行程序时遇到了问题,并且数据库中没有任何数据。
我想查询数据库中最后打开的播放列表,但如果数据库中没有播放列表,我想创建一个空的 PlayList 对象。
7 public class PlayListRepository
8 {
9 public PlayListRepository(Application application)
10 {
11 _application = application;
12 }
13
14 public LiveData<PlayListWithTracks> getPlayList(int playListId)
15 {
16 if (_appDao == null) {
17 InitDb();
18 }
19 LiveData<PlayListWithTracks> livePlayListWithTracks = _appDao.getByIdWithTracks(playListId);
20 if (livePlayListWithTracks.getValue() == null) {
21 livePlayListWithTracks.setValue(new PlayListWithTracks());
22 }
23 return livePlayListWithTracks;
24 }
25
26
27 private void InitDb()
28 {
29 AppDatabase db = AppDatabase.getDatabase(_application);
30 _appDao = db.appDao();
31 }
32
33 private Application _application;
34 private AppDao _appDao;
35 }
第 21 行无法编译。上面写着error: setValue(T) has protected access in LiveData。
我的AppDao.getByIdWithTracks 方法如下所示:
@Dao
public interface AppDao
{
@Transaction
@Query("SELECT * FROM PlayList WHERE Id = :id")
LiveData<PlayListWithTracks> getByIdWithTracks(int id);
}
我尝试将livePlayListWithTracks 转换为MutableLiveData<PlayListWithTracks>,但这给了我androidx.room.RoomTrackingLiveData cannot be cast to androidx.lifecycle.MutableLiveData 的运行时错误
我尝试将其转换为 RoomTrackingLiveData,但 Android Studio 无法识别 androidx.room 导入。
是我走错了路还是什么?
编辑:这是 PlayListWithTracks:
public class PlayListWithTracks
{
@Embedded
public PlayList playList;
@Relation(
parentColumn = "id",
entityColumn = "playListId"
)
public List<Track> tracks = new Vector<Track>();
}
【问题讨论】:
-
显示 livePlayListWithTracks.setValue 这个方法。请发布 viewModel 类代码
-
视图模型只是调用了上面不会编译的
getPlayList()方法。如果有帮助,我发布了PlayListWithTracks。 -
一般来说,如果你不创建
LiveData,你不能修改LiveData。在这种情况下,您没有创建LiveData-- Room 是创建的。您使用的是 Java,而不是 Kotlin,这限制了您的选择。同样,您使用的是 Room 中的LiveData,而不是 RxJava,这限制了您的选择。也许您可以使用Transformations.map()(例如,在您的视图模型中)来处理这种“提供默认结果”的场景。 -
@MattGregory:“我认为修改数据是 LiveData 的用途”——是的,对于
LiveData的创建者,而不是消费者我>。在这种情况下,您只是消费者。 “一旦从数据库中获取 LiveData 类,我是否应该删除它?” - 通常不会,因为这将是您了解数据库更改的方式。但是,这取决于场景。 “然后将有效负载包装在 MutableLiveData 中,因为我需要它来监控用户所做的更改?” -- 通常,您会将用户更改存储在数据库本身中。但是,同样,这取决于场景。 -
@MattGregory:您可以创建
LiveData的子类,或使用MutableLiveData,或使用MediatorLiveData,既是LiveData的创建者又(可能)是消费者。但是,如果您从其他人(例如 Room 或其他图书馆)获得LiveData,那么您只是消费者。
标签: java android android-room