如何将C#泛型类型传递给另一个类

Fro*_*art 2 c# generics

有没有办法在C#中编写以下代码?

public T GetRandomRecord<T>(DbSet<T> set)
{
    return set.OrderBy(r => Guid.NewGuid()).FirstOrDefault();
}
Run Code Online (Sandbox Code Playgroud)

它给了我以下错误:

错误CS0452类型'T'必须是引用类型才能在泛型类型或方法'DbSet'中将其用作参数'TEntity'

DbSet是的Microsoft.EntityFrameworkCore.DbSet.

我该如何解决?

15e*_*153 9

尝试泛型类型约束.class在此上下文中将约束T为引用类型.调用者将无法调用GetRandomRecord<DateTime>(dbSet),因为它DateTime是一个结构.这将由编译器强制执行.

public T GetRandomRecord<T>(DbSet<T> set) where T : class
{
    // ... stuff
}
Run Code Online (Sandbox Code Playgroud)

这是必需的,因为DBSet<TEntity>具有相同的约束:

public class DbSet<TEntity> 
    : DbQuery<TEntity>, 
      IDbSet<TEntity>, 
      IQueryable<TEntity>, 
      IEnumerable<TEntity>, 
      IQueryable, 
      IEnumerable 
      where TEntity : class
    //  M... O... U... S... EEEEE....
{
Run Code Online (Sandbox Code Playgroud)

所以编译器不会让你做你正在做的事情,直到你可以保证你会尊重那个约束DbSet.你可以通过对你自己的方法应用相同的约束来提供这种保证,这会告诉编译器让你独自一人,而是在你的调用者身上喷出那个神秘的错误信息.

  • @FrozenHeart在这种情况下,可能是因为`DbSet <T>`对它自己的类型参数`T`有一个相同的约束. (2认同)
  • @FrozenHeart是的,我刚检查过,它有相同的约束.`其中TEntity:class` (2认同)