2012-11-20 80 views
7

可能重複:
Impossible recursive generic class definition?奇怪的C#泛型contraint

我才發現,原來

public class Foo<T> where T : Foo<T> 
{ 

} 

是合法的。這究竟意味着什麼?它似乎 遞歸,是否有可能像這樣實例化 ?

+10

這些被稱爲「好奇地重現」的通用約束。另見:Eric Lippert的[Curiouser and curiouser](http://blogs.msdn.com/b/ericlippert/archive/2011/02/03/curiouser-and-curiouser.aspx),它可能是最好的解釋你可以得到。 – Kobi

+0

這通常用於獲取對實際類的類型引用。例子是IComparable等。 – leppie

+1

@AlvinWong,這不完全沒用。您可以像這樣構建樹狀結構,方法是向Foo添加保存值的屬性。同樣,Foo可以被繼承,因此這個約束將允許Foo的任何派生。 – series0ne

回答

2

我不會說這是無用的。讓我們觀察下面的例子,如何支持流利的語法。在情況下,你是在家長創造一些base實施和願意提供流暢的聲明...您可以使用此約束這樣

public class Parent<TChild> 
    where TChild : Parent<TChild> 
{ 
    public string Code { get; protected set; } 

    public TChild SetCode(string code) 
    { 
     Code = code; 
     return this as TChild; // here we go, we profit from a constraint 
    } 
} 

public class Child : Parent<Child> 
{ 
    public string Name { get; protected set; } 

    public Child SetName(string name) 
    { 
     Name = name; 
     return this // is Child; 
    } 
} 

[TestClass] 
public class TestFluent 
{ 
    [TestMethod] 
    public void SetProperties() 
    { 
     var child = new Child(); 
     child 
      .SetCode("myCode") // now still Child is returned 
      .SetName("myName"); 

     Assert.IsTrue(child.Code.Equals("myCode")); 
     Assert.IsTrue(child.Name.Equals("myName")); 
    } 
} 

請把它只是一個例子,這是如何可以使用約束

+0

有趣的例子。不確定我喜歡它 - 它仍然感覺不對,但我發現它*可能有一些用途... – Grhm