混合泛型方法和扩展方法

tpo*_*pol 5 .net c# generics extension-methods

Class1.GetChild<T>() where T : DependencyObjectlib1.dll程序集中创建了扩展方法.之后,依赖于lib1.dll的所有程序集无法编译并出现错误:

类型'System.Windows.DependencyObject'是在未引用的可配置中定义的.您必须添加对程序集"WindowsBase"等的引用...

为什么依赖程序集需要WindowsBase即使它们不使用GetChild

.

要重现(vs2010 .net4):

lib1.dll(引用WindowsBase)

namespace lib1
{
    public static class Class1
    {
        public static T GetChild<T>(this DependencyObject src) where T : DependencyObject
        {
            return default(T);
        }
    }

    public static class Class2
    {
        public static int SomeExtMethod(this string src)
        {
            return 0;
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

lib2.dll(引用lib1但不是WindowsBase)

using lib1;
class someClass
{
    void someFct()
    {
        "foo".SomeExtMethod(); // error: The type 'System.Windows.DependencyObject'
                // is defined in an assemebly that is not referenced. 
                // You must add a reference to assembly 'WindowsBase' etc..
    }
}
Run Code Online (Sandbox Code Playgroud)

.

更新:

我认为在混合泛型方法和扩展方法时肯定会有一些东西.我尝试在以下示例中演示此问题:

// lib0.dll
namespace lib0
{
    public class Class0 { }
}

// lib1.dll
using lib0;
namespace lib1
{
    public static class Class1
    {
        public static void methodA<T>() where T : Class0 { }    // A
        public static void methodB(Class0 e) { }                // B
        public static void methodC(this int src) { }            // C
    }

    public static class Class2
    {
        public static void methodD(this String s) { }
    }
}

// lib2.dll
using lib1;
class someClass
{
    void someFct()
    {
        Class2.methodD("");  // always compile successfully
        "".methodD();        // raise the 'must add reference to lib0' error depending on config. see details below.
    }
}
Run Code Online (Sandbox Code Playgroud)

A, //B, //C - >编译确定

A, B, //C - >编译确定

//A, B, C - >编译确定

A, //B, C - >提出错误

A, B, C - >提出错误

//A手段methodA评论.正如Damien指出的那样,类型推断可能会发挥一些作用.仍然很想知道这些来龙去脉.

Ami*_*tal 3

Microsoft 已在此处回答您的情况: https://connect.microsoft.com/VisualStudio/feedback/details/668498/problem-with-extension-method-in-c-compiler

还有其他独立于扩展方法的用例会错误地产生此错误。

考虑一下:

  1. 在类型(例如 TP1)中定义通用方法,该方法在库(例如 LB1)中定义。
  2. 类型将泛型方法约束在其他库 LB2 中定义的某些类型上。
  3. 在TP1中定义另一个方法。
  4. 现在在您的库中仅引用 LB1 并尝试调用 TP1 类型的第二个方法

如果您不使用 TP1,而是使用 LB1 中定义的其他类型,则不会收到错误。此外,即使 TP1 类型的方法之一需要 LB2 中定义的类型的参数(并且您不调用此方法),它也不会产生此错误