【问题标题】:How to make a Generic Collection with Type Constraint that implement two interfaces?如何使用实现两个接口的类型约束创建通用集合?
【发布时间】:2011-01-31 18:02:06
【问题描述】:

对不起,我没有在 c# 中处理过很多泛型

according to this question,怎么可能做一个generc集合 实现两个接口 我一直在寻找这样的直接方法:当然会出错,而且完全是错误的。

interface IEmployee {void DisplayInfo();}

interface ISalary {void CalculateSalary();}


class Nurse : IEmployee, ISalary
{
 //some Implementation
}


class Doctor : IEmployee, ISalary
{
 //some Implementation
}

class EntryPoint
{
 static void Main(string[] args)
  { 
  System.Collections.Generic .List<T>  employees where T: ISalary,IEmployee
   =new System.Collections.Generic .List<T>();
  }

 Nurse oNurse = new Nurse();
 Doctor oDoctor = new Doctor();

 employees.Add(oNurse);
 employees.Add(oDoctor);
}

在阅读了一些之后,我发现也许我必须首先定义一个这样的泛型类:

public class HospitalEmployee<T> where T : IEmployee, ISalary

{

}

不幸的是它不起作用,现在我很困惑,不知道该怎么做,请帮助,谢谢你

【问题讨论】:

    标签: c# syntax generics


    【解决方案1】:

    你可以这样做:

    interface IEmployee { void DisplayInfo(); }
    interface ISalaried { void CalculateSalary(); }
    interface ISalariedEmployee : IEmployee, ISalaried {}
    class Doctor : ISalariedEmployee { whatever }
    class Nurse : ISalariedEmployee { whatever }
    ...
    var list = new List<ISalariedEmployee>() { new Nurse(), new Doctor() };
    

    这有帮助吗?

    真正想要的功能基本上不存在。有一种方法可以说“这个泛型类型参数必须用实现这两个接口的类型参数构造”,但奇怪的是,没有一种方法可以说“这个局部变量必须使用对实现这两个接口的对象的引用来初始化”。这只是 C# 类型系统的一个缺点,您可以在类型参数中表示它,但不能在局部变量中表示。你想要的是:

    var list = new List<IEmployee + ISalary>();
    

    现在您只能将实现这两​​个接口的东西放入列表中。但不幸的是,C# 中没有这样的功能。对不起!

    【讨论】:

    • 嗨 lipprt 先生,很高兴在这篇文章中见到您,您的解决方案救了我,谢谢,但只是出于好奇,我想知道是否可以在不使用组合接口的情况下处理这个问题?跨度>
    • 再次感谢您的更新,如果 C# 团队能够涵盖此内容,那就太好了。当然我不是理想主义者。-)
    • 一个更有用的通用解决方案是类型模式匹配或类型类:)
    • @James Dunne:看到一个通用的解决方案非常有趣和有吸引力,您能否为您的建议提供一些代码,这将非常有用,非常感谢您
    • @siamak:詹姆斯在开玩笑。 C# 不支持这些功能。 F# 或 Haskell 等函数式语言在其类型系统中具有这些特性。
    【解决方案2】:

    不清楚您要做什么:创建自己的通用容器或使用List&lt;T&gt; 来存储不同的对象。

    但据我了解,您需要这样的东西:

    List<IEmployee> employees = new List<IEmployee>();
    Nurse oNurse = new Nurse();
    Doctor oDoctor = new Doctor();
    
    employees.Add(oNurse);
    employees.Add(oDoctor);
    

    更新

    只需创建一个继承所有要使用的接口的接口,例如:

    interface IEmployeeWithSalery: IEmployee, ISalery {}
    List<IEmployeeWithSalery> employees = new List<IEmployeeWithSalery>()
    

    【讨论】:

    • 我只想有一个实现两个接口(ISalary 和 Iemployee)的对象列表,看来您的解决方案适用于一个接口
    • 回复:您的更新:是什么让 Doctor 神奇地实现了 IEmployeeWithSalary,如果它还没有实现?问题的关键在于,泛型类型参数的有效接口集使您能够表达实现两个接口的类型的交集而无需诉诸从这两个接口派生的第三个接口。但是没有办法在泛型类型参数的有效接口集之外的类型系统中表达这一点。
    【解决方案3】:

    这听起来很像我几周前提出的问题Storing an object that implements multiple interfaces and derives from a certain base (.net)。我在那里提供了一种可能的解决方法,它可能比定义和使用一些“组合”接口类型更有效,但它的优点是可以定义一个对象以使用任何特定的接口组合,这些接口的任何特定组合都经过适当定义,而无需定义该组合的新“组合”接口类型。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-11-28
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多