EF Core 中索引通过 OnModelCreating 中的 HasIndex 配置,支持单列、多列、唯一、过滤(SQL Server)和包含列(SQL Server);需经迁移才生效,命名可自定义,设计时应结合查询模式避免滥用。

EF Core 中设置索引主要通过 HasIndex 方法在 Fluent API 中配置,它支持单列、多列、唯一、过滤(SQL Server)、包含列(SQL Server)等多种索引类型。关键点是:索引定义写在 OnModelCreating 里,迁移生成后才真正创建到数据库。
基础单列索引
最常用场景:为高频查询字段(如 Email、Status)加索引提升查询速度。
示例:为 User.Email 添加普通索引
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity()
.HasIndex(u => u.Email); // 默认非唯一
}
生成的迁移代码会调用 CreateIndex,数据库执行后生效。
唯一索引与多列索引
防止重复数据或组合查询优化时非常实用。
-
唯一索引:加
IsUnique() - 多列索引:传入匿名对象或元组,顺序影响查询效率
// 唯一索引:确保邮箱不重复 modelBuilder.Entity() .HasIndex(u => u.Email) .IsUnique(); // 多列索引:按 (Status, CreatedAt) 查询快 modelBuilder.Entity () .HasIndex(o => new { o.Status, o.CreatedAt });
高级选项:过滤索引与包含列(SQL Server)
仅 SQL Server 支持,适合稀疏数据或覆盖查询场景。
-
过滤索引:只对满足条件的数据建索引(如
Status = 'Active') - 包含列:把非键列加入索引叶节点,避免回表
modelBuilder.Entity() .HasIndex(u => u.Email) .HasFilter("[Status] = 'Active'") // SQL 表达式 .IncludeProperties(u => u.FirstName); // 包含 FirstName 列
注意:HasFilter 和 IncludeProperties 是 SQL Server 特有,其他数据库迁移会忽略或报错。
索引命名与性能提醒
EF Core 默认为索引生成名称(如 IX_Users_Email),也可手动指定:
.HasIndex(u => u.Email)
.HasName("IX_Users_Email_Verified");
小建议:
- 别盲目加索引——写多读少的表加索引反而拖慢插入/更新
- 复合索引注意字段顺序:等值查询字段放前,范围查询字段放后(如
WHERE Status = 1 AND CreatedAt > '2024',索引应为(Status, CreatedAt)) - 迁移前用
dotnet ef migrations script查看实际 SQL,确认索引是否符合预期
基本上就这些。HasIndex 看似简单,但结合业务查询模式合理设计,才能真正提升性能。










