2011-05-09 88 views
2

我剛剛讓不幸(至少對於我的應用程序)發現在泛型類中聲明的兩個方法沒有相同的基本定義,在代碼中表現得最好:確定兩個方法是否具有相同的基本定義

public static class Test 
    { 
     private class Generic<T> { public void Method() { } } 
     public static void TestBase() 
     { 
      var x = typeof(Generic<int>).GetMethod("Method"); 
      var y = typeof(Generic<double>).GetMethod("Method"); 
      Debug.Assert(x.GetBaseDefinition() == y.GetBaseDefinition()); // fails 
     } 
    } 

x和y.IsGeneric都是false,因此無法使用GetGenericMethodDefinition。

我已經能夠想象的,到目前爲止唯一的解決辦法是比較他們的名字,他們的聲明類型相同泛型類型,但在過載的情況下,似乎很脆..

所以..我不認爲有一個有用的方法,我已經錯過了反射庫,可以告訴我,如果這兩個方法已經在同一個類中首次聲明?還是解決方法?

編輯:

爲了澄清,我想打一個方法:

public bool DeclaredInSameClass(MethodInfo a, MethodInfo b); 

如果A和B都在同一個班都首先聲明返回true。

忽略泛型,這很簡單:a.GetBaseDefinition() == y.GetBaseDefinition(),但如何處理泛型類中聲明的方法?

+0

難道你不只是要求,看看是否MethodsCollection包含於所選的MethodInfo的參考?也許是一個用例來說明什麼時候這會有用? – Tejs 2011-05-09 19:14:31

+0

模板的兩種實現之間的類型不同的事實意味着它們根據定義是不同的。你說你想看看它們是否在同一個班級中定義,但是通用與通用不同。 – 2011-05-09 19:18:43

+0

@ James(/ Tejs),不幸的是,他們在同一個班上宣佈對我來說意義重大。基本上我希望能夠知道兩個共享一堆屬性的類是否有任何共同的部分 - 允許將設置從一個類複製到另一個類。這不僅適用於任何類 - 我確實擁有對類的控制權,而且僅供內部使用,但它對於瞭解這些內容非常有用。儘管如此,屬性使事情變得更復雜,所以我很樂意將問題留在方法上;)。這一切都工作得很好,直到泛型涉足我可能會添加.. – Mania 2011-05-09 19:27:03

回答

5

編輯...一個最後一次嘗試:

private class Generic<T> { 
     public void Method() { } 
     public void Method(string param) { } 
     public void OtherMethod() { } 
    } 
    private class NonGeneric { public void Method() { } } 
    static void Main(string[] args) 
    { 
     var x = typeof(Generic<int>).GetMethod("Method", new Type[]{}); 
     var y = typeof(Generic<double>).GetMethod("Method", new Type[]{}); 
     var a = typeof(Generic<double>).GetMethod("OtherMethod"); 
     var b = typeof(NonGeneric).GetMethod("Method"); 
     var c = typeof(Generic<int>).GetMethod("Method", new Type[] { typeof(string) }); 

     Debug.Assert(DeclaredInSameClass(x, y)); 
     Debug.Assert(!DeclaredInSameClass(x, a)); 
     Debug.Assert(!DeclaredInSameClass(x, b)); 
     Debug.Assert(!DeclaredInSameClass(x, c)); 
     Debug.Assert(!DeclaredInSameClass(a, b)); 

    } 

    public static bool DeclaredInSameClass(MethodInfo a, MethodInfo b) 
    { 
     if (a.DeclaringType.IsGenericType != b.DeclaringType.IsGenericType) 
     { 
      return false; 
     } 
     else if (a.DeclaringType.IsGenericType) 
     { 

      var x = a.DeclaringType.GetGenericTypeDefinition().GetMethod(a.Name, a.GetParameters().Select(p => p.ParameterType).ToArray()); 
      var y = b.DeclaringType.GetGenericTypeDefinition().GetMethod(b.Name, b.GetParameters().Select(p => p.ParameterType).ToArray()); 
      return x.Equals(y); 
     } 
     return a.GetBaseDefinition().Equals(b.GetBaseDefinition()); 
    } 
+0

我真的希望不訴諸解決方法的名稱,我意識到在我做的例子 - 但在真正的應用程序,我已經有兩個MethodInfos。抓住他們的名字,並在存在重載和財產隱藏(與新操作員)的情況下尋找他們等將爲我打破。大家都太熟悉AmbiguousMatchException .. – Mania 2011-05-09 18:53:05

+0

你應該澄清這個問題...我只是讓你的測試通過失敗 – 2011-05-09 18:56:44

+0

@mania - 看到更新只改變了斷言條件 – 2011-05-09 19:02:12

相關問題