2013-03-23 54 views
2

在C#中使用泛型時,我被奇怪的行爲難倒了。考慮以下代碼:未綁定泛型類型的C#基類不可用?

class CEmployee<T> { } 
class CManager<T> : CEmployee<T> { } 

class Program 
{ 
    static void Main(string[] args) 
    { 
     CManager<String> cemp = new CManager<String>(); 
     Console.WriteLine(cemp.GetType()); 
     Console.WriteLine(cemp.GetType().FullName); 
     Console.WriteLine(cemp.GetType().BaseType); 
     Console.WriteLine(cemp.GetType().BaseType.FullName); 
     Console.WriteLine(1); 
     Console.WriteLine(cemp.GetType().GetGenericTypeDefinition()); 
     Console.WriteLine(cemp.GetType().GetGenericTypeDefinition().FullName); 
     Console.WriteLine(cemp.GetType().GetGenericTypeDefinition().BaseType); 
     Console.WriteLine(cemp.GetType().GetGenericTypeDefinition().BaseType.FullName); // Problem 1 
     Console.WriteLine(2); 
     Console.WriteLine(typeof(CManager<>)); 
     Console.WriteLine(typeof(CManager<>).FullName); 
     Console.WriteLine(typeof(CManager<>).BaseType); 
     Console.WriteLine(typeof(CManager<>).BaseType.FullName); // Problem 1 
     Console.WriteLine(3); 
     Console.WriteLine(typeof(CManager<>).Equals(cemp.GetType().GetGenericTypeDefinition())); 
     Console.WriteLine(typeof(CEmployee<>).Equals(cemp.GetType().GetGenericTypeDefinition().BaseType)); // Problem 2 


    } 
} 

輸出是

ConsoleApplication1.CManager`1[System.String] 
ConsoleApplication1.CManager`1[[System.String, mscorlib, Version=4.0.0.0, Culture=neutr 
ConsoleApplication1.CEmployee`1[System.String] 
ConsoleApplication1.CEmployee`1[[System.String, mscorlib, Version=4.0.0.0, Culture=neut 
1 
ConsoleApplication1.CManager`1[T] 
ConsoleApplication1.CManager`1 
ConsoleApplication1.CEmployee`1[T] 

2 
ConsoleApplication1.CManager`1[T] 
ConsoleApplication1.CManager`1 
ConsoleApplication1.CEmployee`1[T] 

3 
True 
False 

我難倒,爲什麼基類中的未綁定的泛型類型是不完全可用:

  1. 爲什麼我收到什麼時候我得到基地的全名 類型的未綁定的泛型? (在上面的代碼「問題1」)
  2. 爲什麼如果我的CManager實例的基本類型是 CEmployee,和基類中的未結合的 類型的CManager <類型>是CEmployee <>,和未結合的類型CManager 「等於」我的實例的泛型類型定義,未綁定類型的基類型 不等於泛型的類型定義的基類型 我的實例? (在上面的代碼 「問題2」)

回答

7

在相反的順序:

2:因爲基類型是CEmployee<T>,不CEmployee<>。它們是有區別的; CEmployee<>是類型定義; CEmployee<T>從父類型綁定到T。您可以通過查看IsGenericTypeDefinitionGetGenericArguments()[0]

1:因爲這種通用類型形式的FullName未定義。這是fully documented

如果當前類型包含沒有被替換特定類型的泛型類型參數(即,ContainsGenericParameters屬性返回true),但是該類型不是泛型類型定義(即, IsGenericTypeDefinition屬性返回false),該屬性返回null。

這正是我們在「2」中所討論的。

+0

確實!這就解釋了爲什麼如果#2你把BaseGenericTypeDefinition放在BaseType之後,它確實有效。 – Mishax 2013-03-23 08:14:56