C#泛型类型中的“当前类型”占位符?

时间:2010-08-30 10:49:01

标签: c# .net generics

基本上,我想做的是:

public class MySpecialCollection<T>
    where T : ISomething { ... }

public interface ISomething
{
    public ISomething NextElement { get; }
    public ISomething PreviousElement { get; }
}

public class XSomething : ISomething { ... }

MySpecialCollection<XSomething> coll;
XSomething element = coll.GetElementByShoeSize(39);
XSomething nextElement = element.NextElement; // <-- line of interest

...无需将nextElement转换为XSomething。有任何想法吗? 我本来想要的东西......

public interface ISomething
{
    public SameType NextElement { get; }
    public SameType PreviousElement { get; }
}

提前谢谢!

3 个答案:

答案 0 :(得分:10)

使界面通用:

public class MySpecialCollection<T> where T : ISomething<T> {
  ...
}

public interface ISomething<T> {
  T NextElement { get; }
  T PreviousElement { get; }
}

public class XSomething : ISomething<XSomething> {
  ...
}

答案 1 :(得分:1)

好吧,你可以使用隐式运算符(虽然我不是100%确定它在这种情况下会起作用):

public static XSomething operator implicit(ISomething sth)
{
     return (XSomething)sth;
}

但请注意,这显然不是一个好主意;最干净的方法是做一个明确的演员。

答案 2 :(得分:1)

我建议使接口通用,这样属性的类型就可以是接口的泛型类型。

using System;

namespace ConsoleApplication21
{
    public interface INextPrevious<out TElement>
    {
        TElement NextElement { get; }
        TElement PreviousElement { get; }
    }

    public class XSomething : INextPrevious<XSomething>
    {
        public XSomething NextElement
        {
            get { throw new NotImplementedException(); }
        }

        public XSomething PreviousElement
        {
            get { throw new NotImplementedException(); }
        }
    }

    public class MySpecialCollection<T>
        where T : INextPrevious<T>
    {
        public T GetElementByShoeSize(int shoeSize)
        {
            throw new NotImplementedException();
        }
    }

    class Program
    {
        static void Main(string[] args)
        {
            var coll = new MySpecialCollection<XSomething>();
            XSomething element = coll.GetElementByShoeSize(39);
            XSomething nextElement = element.NextElement;
        }
    }
}