作者:月星名店_882 | 来源:互联网 | 2023-02-01 15:54
我正在使用最近在Google I/O上宣布的Android架构组件中的Android的Room Persistence Library.事情似乎有效,但我收到以下错误:
警告:tagId列引用外键但它不是索引的一部分.每当修改父表时,这可能会触发全表扫描,因此强烈建议您创建一个涵盖此列的索引.
我的数据库有3个表:Note
,Tag
,和JoinNotesTags
.对标记的注释是多对多关系,因此JoinNotesTags表用于处理映射.表格很简单:
Note.id
并且Tag.id
都是主键
JoinNotesTags.noteId
引用 Note.id
JoinNotesTags.tagId
引用 Tag.id
外键约束在JoinNotesTags
表上定义.作为参考,这是表的CREATE TABLE
声明JoinNotesTags
:
"CREATE TABLE IF NOT EXISTS `JoinNotesTags` (
`id` INTEGER PRIMARY KEY AUTOINCREMENT,
`noteId` INTEGER,
`tagId` INTEGER,
FOREIGN KEY(`noteId`) REFERENCES `Note`(`id`) ON UPDATE NO ACTION ON DELETE CASCADE ,
FOREIGN KEY(`tagId`) REFERENCES `Tag`(`id`) ON UPDATE NO ACTION ON DELETE NO ACTION
)"
这是@Entity
该类的相应注释:
@Entity(
indices = arrayOf(Index(value = *arrayOf("noteId", "tagId"), unique = true)),
foreignKeys = arrayOf(
ForeignKey(
entity = Note::class,
parentColumns = arrayOf("id"),
childColumns = arrayOf("noteId"),
OnDelete= ForeignKey.CASCADE),
ForeignKey(
entity = Tag::class,
parentColumns = arrayOf("id"),
childColumns = arrayOf("tagId"))
)
)
从@Entity
注释中可以看出,tagId
它包含在复合唯一索引中noteId
.我已经确认在自动生成的json模式文件中也正确定义了这个索引:
"CREATE UNIQUE INDEX `index_JoinNotesTags_noteId_tagId`
ON `JoinNotesTags` (`noteId`, `tagId`)"
所以,我的问题:这个警告只是(仍然是alpha版本的)房间库中的一个错误 - 即编译时分析缺少tagId
这个复合索引的一部分吗?或者我是否真的有一个索引问题,我需要解决,以避免全表扫描?
1> Prakash..:
您需要为列添加索引以便更快地进行查询以下是一个示例
@Entity(indices = {@Index("artist_id")})
public class Artist{
@NonNull
@PrimaryKey
@ColumnInfo(name = "artist_id")
public String id;
public String name;
}
2> 小智..:
当使用kotlin代码时:
之前
@Expose
@SerializedName("question_id")
@ColumnInfo(name = "question_id")
var questionId: Long
后
@Expose
@SerializedName("question_id")
@ColumnInfo(name = "question_id", index = true) //just add index = true
var questionId: Long
3> CL...:
修改Tag
表时,数据库可能需要查找JoinNotesTags
表中的相应行.为了提高效率,这需要tagId
列上的索引.
您的复合索引对此无用; 由于索引的工作方式,要搜索的列必须是索引中最左边的列.
您应该只在tagId
列上添加索引.(你可以交换复合索引中列的顺序,但是你会遇到同样的问题noteId
.)
你能添加样本插图吗?
@AshishKrishnan是的,两者都应该是索引中最左边的列。