C# 如何制作这种通用方法?

C# 如何制作这种通用方法?,c#,generics,C#,Generics,这是对我之前关于规范模式的问题的改进 我正在尝试将SalesSpecificationForBook的方法设置为通用方法。原因是AudioCD逻辑也需要类似的规范,Book和AudioCD都实现了IselingItem接口 规范 public class OnSaleSpecificationForBook : Specification<Book> { public override bool IsSatisfiedBy(Book product) {

这是对我之前关于规范模式的问题的改进

我正在尝试将SalesSpecificationForBook的
方法设置为通用方法。原因是AudioCD逻辑也需要类似的规范,
Book
AudioCD
都实现了
IselingItem
接口

规范

public class OnSaleSpecificationForBook : Specification<Book>
{
    public override bool IsSatisfiedBy(Book product)
    {
        return product.IsOnSale;
    }
}

您需要指定泛型参数的类型,然后编译器才能知道它是
ISellingItem
。您可以使用
where T:ISellingItem
子句:

public class OnSaleSpecification<T> : Specification<T> where T : ISellingItem
{
    public override bool IsSatisfiedBy(T item)
    {
        return item.IsOnSale;
    }
}
SalesSpecification上的公共类:其中T:ISellingItem的规范 { 公共覆盖布尔满足(T项) { 退货项目。不可销售; } }
您的SalesSpecification类需要定义泛型参数T并将其约束到ISellingItem

public class OnSaleSpecification<T> : Specification<T> where T : ISellingItem
{
    public override bool IsSatisfiedBy(T item)
    {
        return item.IsOnSale;
    }
}
SalesSpecification上的公共类:其中T:ISellingItem的规范 { 公共覆盖布尔满足(T项) { 退货项目。不可销售; } }
如果没有对
t
的约束,这将无法工作,因为它没有
IsOnSale
属性。除非您也将
onSalesSpecification
设置为泛型,否则这将无法编译。Lijo:我已经编辑了答案@伊恩·麦克莱尔德:接得好。谢谢。@IanMcLaird当我们将
设置为泛型时,编译器的优势是什么?换句话说,为什么编译器强制类是泛型的?否则会发生什么?不能扩展未绑定的泛型类型。所有类型参数(本例中为
)都必须在
之前定义,或者是一个明确的已知类型。还要注意,在这种特定情况下,您可以在SalesSpecification:Specification上将其设置为
,而不会丢失此方法的功能。但是,如果这样做,您将无法添加实际关心实际类型的其他方法。引用:
class Program
{       
    static void Main(string[] args)
    {
        List<Book> list = new List<Book>();

        Book p1 = new Book(false, 99);
        Book p2 = new Book(true, 99);
        Book p3 = new Book(true, 101);

        list.Add(p1);
        list.Add(p2);
        list.Add(p3);

        var specification = new OnSaleSpecificationForBook();
        List<Book> selectedList =
            ProductFilterHelper.GetProductsUisngDynamicFilters(list, specification);
    }
}

public static class ProductFilterHelper
{
    public static List<Book> GetProductsUisngDynamicFilters(List<Book> productList, Specification<Book> productSpecification)
    {
        return productList.Where(p => productSpecification.IsSatisfiedBy(p))
                          .ToList();
    }
}
public class Book : ISellingItem
{
    public bool IsOnSale { get; set; }
    public double Price { get; set; }

    public Book(bool isOnSale, double price)
    {
        this.Price = price;
        this.IsOnSale = isOnSale;
    }
}

public class AudioCD : ISellingItem
{
    public bool IsOnSale { get; set; }
    public double Price { get; set; }

    public AudioCD(bool isOnSale, double price)
    {
        this.Price = price;
        this.IsOnSale = isOnSale;
    }
}
public class OnSaleSpecification<T> : Specification<T> where T : ISellingItem
{
    public override bool IsSatisfiedBy(T item)
    {
        return item.IsOnSale;
    }
}
public class OnSaleSpecification<T> : Specification<T> where T : ISellingItem
{
    public override bool IsSatisfiedBy(T item)
    {
        return item.IsOnSale;
    }
}