List EF Core中的枚举列表
是否可以在使用EF Core的项目中使用枚举列表来存储数据 我的枚举:List EF Core中的枚举列表,list,asp.net-core,enums,ef-core-3.1,List,Asp.net Core,Enums,Ef Core 3.1,是否可以在使用EF Core的项目中使用枚举列表来存储数据 我的枚举: public enum AudienceType { Child, Teen, [Display(Name ="Young Adult")] YoungAdult, Adult, Elderly } 使用枚举初始化: public class Restaurant { publi
public enum AudienceType
{
Child,
Teen,
[Display(Name ="Young Adult")]
YoungAdult,
Adult,
Elderly
}
使用枚举初始化:
public class Restaurant
{
public int Id { get; set; }
[Required, StringLength(80)]
public string Name { get; set; }
[Display(Name="Select the target audiences")]
public List<AudienceType> AudienceTypes { get; set; }
}
更新:
我了解了如何使用值转换来处理枚举,如下所示:
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
var converter = new EnumToStringConverter<AudienceType>();
modelBuilder
.Entity<Restaurant>()
.Property(e => e.AudienceTypes)
.HasConversion(converter);
}
模型创建时受保护的覆盖无效(ModelBuilder ModelBuilder)
{
基于模型创建(modelBuilder);
var converter=新的EnumToStringConverter();
建模者
.实体()
.Property(e=>e.AudienceType)
.转换(转换器);
}
但是如何处理枚举列表呢?要将枚举值列表表示为逗号分隔的字符串,可以使用值转换 最简单的“内联”选项:
//在DbContext类中
模型创建时受保护的覆盖无效(ModelBuilder ModelBuilder)
{
建模者
.实体()
.Property(e=>e.AudienceType)
.哈斯转换(
v=>string.Join(v.Select(e=>e.ToString(“D”)).ToArray(),
v=>v.Split(新[]{',})
.Select(e=>Enum.Parse(typeof(audenceType),e))
.Cast()
托利斯先生()
);
}
因为enum不是一个类,所以需要编写一个新类来封装它
您可以创建一个新类:
public class Audience
{
public int Id { get; set; }
public AudienceType AudienceType { get; set; }
}
然后在您的餐厅
:
public class Restaurant
{
public int Id { get; set; }
[Required, StringLength(80)]
public string Name { get; set; }
[Display(Name="Select the target audiences")]
public List<Audience> Audiences{ get; set; }
}
公共级餐厅
{
公共int Id{get;set;}
[所需长度(80)]
公共字符串名称{get;set;}
[显示(Name=“选择目标受众”)]
公共列表访问群体{get;set;}
}
如果需要转换,可以在dbcontext中进行转换
modelBuilder.Entity<Audience>().Property(b => b.AudienceType).HasConversion(
v => v.ToString(), v => (AudienceType)Enum.Parse(typeof(AudienceType), v));
modelBuilder.Entity().Property(b=>b.AudienceType).HasConversion(
v=>v.ToString(),v=>(AudienceType)Enum.Parse(typeof(AudienceType),v));
然后迁移和更新数据库。您将获得它们之间的一对多关系。我发现这很有用,这导致了以下解决方案:
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
var converter = new EnumCollectionJsonValueConverter<AudienceType>();
var comparer = new CollectionValueComparer<AudienceType>();
modelBuilder.Entity<Restaurant>()
.Property(e => e.AudienceTypes)
.HasConversion(converter)
.Metadata.SetValueComparer(comparer);
}
模型创建时受保护的覆盖无效(ModelBuilder ModelBuilder)
{
基于模型创建(modelBuilder);
var converter=new EnumCollectionJsonValueConverter();
var comparer=新的CollectionValueComparer();
modelBuilder.Entity()
.Property(e=>e.AudienceType)
.HasConversion(转换器)
.Metadata.SetValueComparer(比较器);
}
它使用以下两个类:
public class EnumCollectionJsonValueConverter<T> : ValueConverter<ICollection<T>, string> where T : Enum
{
public EnumCollectionJsonValueConverter() : base(
v => JsonConvert
.SerializeObject(v.Select(e => e.ToString()).ToList()),
v => JsonConvert
.DeserializeObject<ICollection<string>>(v)
.Select(e => (T)Enum.Parse(typeof(T), e)).ToList())
{
}
}
public class CollectionValueComparer<T> : ValueComparer<ICollection<T>>
{
public CollectionValueComparer() : base((c1, c2) => c1.SequenceEqual(c2),
c => c.Aggregate(0, (a, v) => HashCode.Combine(a, v.GetHashCode())), c => (ICollection<T>)c.ToHashSet())
{
}
}
公共类EnumCollectionJsonValueConverter:ValueConverter其中T:Enum
{
public EnumCollectionJsonValueConverter():base(
v=>JsonConvert
.SerializeObject(v.Select(e=>e.ToString()).ToList()),
v=>JsonConvert
.反序列化对象(v)
.Select(e=>(T)Enum.Parse(typeof(T),e)).ToList()
{
}
}
公共类集合ValueComparer:ValueComparer
{
public CollectionValueComparer():基((c1,c2)=>c1.SequenceEqual(c2),
c=>c.Aggregate(0,(a,v)=>HashCode.Combine(a,v.GetHashCode()),c=>(ICollection)c.ToHashSet())
{
}
}
您希望如何在数据库中“表示”枚举列表?逗号分隔的字符串或例如每个枚举值都有一个单独的表是一条记录。我对逗号分隔的字符串没意见。然后看看我知道如何使用值转换来处理枚举,但是如何处理枚举列表?当我尝试此操作时,HasVersion的第一个参数出现错误:无法从'System.Collections.Generic.IEnumerable'转换为'char'
使用char数组替换Split
方法的参数。如果我将HasConversion的第一个参数替换为'v=>string.Join(,“,”,v.选择(s=>s.ToString()).ToArray()`然后v.Split(“,”)
在第二个参数中生成以下错误:表达式树可能不包含使用可选参数的调用或调用
我喜欢枚举的便利性,我可以直接在razor页面中使用它:
有没有一种简单的方法可以对类执行此操作?(可能我缺少它)courine
是您的枚举吗?很抱歉,复制了错误的代码行,已将其修复。这没关系,但绑定模型时会出现问题,这会使问题变得复杂。因此,如果您想要进行模型绑定,您的方法确实更简单。
public class EnumCollectionJsonValueConverter<T> : ValueConverter<ICollection<T>, string> where T : Enum
{
public EnumCollectionJsonValueConverter() : base(
v => JsonConvert
.SerializeObject(v.Select(e => e.ToString()).ToList()),
v => JsonConvert
.DeserializeObject<ICollection<string>>(v)
.Select(e => (T)Enum.Parse(typeof(T), e)).ToList())
{
}
}
public class CollectionValueComparer<T> : ValueComparer<ICollection<T>>
{
public CollectionValueComparer() : base((c1, c2) => c1.SequenceEqual(c2),
c => c.Aggregate(0, (a, v) => HashCode.Combine(a, v.GetHashCode())), c => (ICollection<T>)c.ToHashSet())
{
}
}