【问题标题】:Auto increment property not key自动递增属性不是键
【发布时间】:2015-01-09 09:55:38
【问题描述】:

是否可以自动增加不是实体框架中主键的属性?我所拥有的是一个有 ID 和序列号的类:

public class Maintenance
{
    [Key]
    public int ID { get; set; }
    public int GroupID { get; set; }
    public int SerialNo { get; set; } 
}

我在GroupIDSerialNo 上有一个具有唯一关系的索引,这使得一个组不可能有两次相同的序列号。

我目前正在做的是在该组中检查.Max() 中的SerialNo。但是,如果序列号自动增加,我会喜欢它。这可能吗?

我一直在寻找解决方案,但据我了解,实体框架不可能有 2 个自动递增列,并且自动递增列将始终是 PK 列。

有没有办法设置自动增量,或者有没有比使用Max() 更好的解决方案?使用Max() 理论上可能会产生两个相同的值,并会导致程序在尝试插入时崩溃(因为唯一索引)。

我先使用代码。

澄清一下:我想保留 ID 作为主键,并在插入时计算序列号。

更新:

我尝试在SerialNo 上使用[DatabaseGenerated(DatabaseGeneratedOption.Identity)],这导致实体框架想要更改此属性的主键。我也试过[DatabaseGenerated(DatabaseGeneratedOption.Computed)],它试图将NULL插入SerialNo列,[DatabaseGenerated(DatabaseGeneratedOption.None)]试图插入0,基本上什么都不做。

要求的信息:

这是表格外观的示例:

|_ID_|_GroupID_|_SerialNo_|
|  1 |    1    |    1     |
|  2 |    1    |    2     |
|  3 |    2    |    1     |
|  4 |    1    |    3     |
|  5 |    2    |    2     |

【问题讨论】:

  • 您找到解决方案了吗?我有同样的问题/问题...
  • 不,抱歉@Mike 我没有。我还在用.Max()

标签: c# entity-framework ef-code-first


【解决方案1】:

是的,您可以使用following attribute

[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int SerialNo { get; set; } 

有关可能的数据注释列表,请参阅HERE

【讨论】:

  • 您好,感谢您的链接。这将非常有帮助。使用DatabaseGenerationOption.Identity 将强制SerialNo 成为对象的主键,这不是我想要的。我想保留 ID 作为主键,并在插入时计算序列号。
  • @RobinDorbell: I want to keep the ID as primary key, and compute the serial number while inserting. - 这绝对有道理,但不是你要求的;-)。也许你可以给我们一些例子你的行应该/可以是什么样子?
  • 这是DatabaseGeneratedOption 而不是DatabaseGenerationOption
  • @JoSmo:感谢您的发现-实际上在我链接到的官方 EF 页面上也是错误的-> 我会给他们发个便条...
【解决方案2】:

如果您使用的是 EF Core,则应使用序列作为解决方案。

    public class Project
    {
      [Key]
      [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
      public int Id { get; set; }
      public int ProjectId { get; set; }
    }

然后配置你的 onModelBuilder:

modelBuilder.HasSequence<int>("ProjectId").StartsAt(100).IncrementsBy(1);
modelBuilder.Entity< Project>().Property(o => o.ProjectId).HasDefaultValueSql("NEXT VALUE FOR ProjectId");

或者您可以在docs 上阅读更多信息。

【讨论】:

    【解决方案3】:

    如果你使用的是 sql server 也请仔细阅读本文

    Can we have more than one identity columns in a table.


    所以我认为下面的代码可以编译,但在尝试迁移/创建数据库时会给你一个错误。

    你也可以像这样使用流利的 api 方法

    protected override void OnModelCreating(DbModelBuilder modelBuilder)
    {
        modelBuilder.Entity<Maintenance>().Property(a => a.GroupID 
                              ).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
        modelBuilder.Entity<Maintenance>().Property(a => a.SerialNo 
                              ).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity);
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-08-07
      • 2016-04-22
      • 1970-01-01
      • 2012-03-13
      相关资源
      最近更新 更多