des*_*lsj 3 c# extension-methods
我有以下两种扩展方法(方法的主体对我的问题不是特别重要,但无论如何包括代码)
public static class DictionaryExtensions
{
public static TValue GetValue<TKey, TValue>(this IDictionary<TKey, TValue> source, TKey key, TValue defaultValue)
{
return (source.ContainsKey(key) ? source[key] : defaultValue);
}
}
public static class WebExtensions
{
public static T GetValue<T>(this HttpContext context, string name, T defaultValue)
{
object value = context.Request.Form[name] ?? context.Request.QueryString[name];
if (value == null) return defaultValue;
return (T)value;
}
}
Run Code Online (Sandbox Code Playgroud)
这两个方法共享相同的名称,但它们扩展了两种非常不同的类型.我希望以下代码很简单,编译器能够选择适当的扩展方法:
var myDict = new Dictionary<int, string>()
{
{ 1, "foo" },
{ 2, "bar" }
};
var result = myDict.GetValue(5, "baz");
Run Code Online (Sandbox Code Playgroud)
但是,由于某些未知原因,Visual Studio拒绝使用以下编译时错误编译我的代码:"类型'System.Web.HttpContext'在未引用的程序集中定义.您必须添加对程序集的引用' System.Web'".此错误告诉我编译器选择了WebExtensions类中的GetValue扩展方法,而不是DictionaryExtension类中的GetValue扩展方法.
我能够解决以下问题:
var result = DictionaryExtensions.GetValue(myDict, 5, "baz");
Run Code Online (Sandbox Code Playgroud)
但我试图理解为什么编译器首先被混淆了.有人知道为什么吗?
另一种选择是将2个Extension类分解为单独的名称空间,并且不要using在WebExtensions类消耗代码中添加类.这样编译器不会尝试解决GetValue到WebExtensions.
只需按照编译器所说的操作并添加对 System.Web.dll 的引用即可。然后它应该编译。
这些扩展方法类所在的外部程序集依赖于 System.Web.dll。编译器应该能够找出重载,但为了做到这一点,它需要引用HttpContext存在的程序集,该程序集位于 System.Web.dll 中。
另一方面,如果您不希望使用扩展方法程序集的项目依赖于 System.Web.dll,则需要在单独的程序集中定义这 2 个扩展方法类。
@Steve Danner 也有一个很好的解决方案:将两个扩展方法类放入同一程序集中的不同命名空间中,并省略包含该类的命名空间的 using 语句WebExtensions。
我偶尔会遇到类似 System.Runtime.Serialization、System.ServiceModel.Activation 等问题。当您有两次删除的依赖项时,可能会发生这种情况。换句话说,您的根项目依赖于一个程序集,而该程序集又依赖于另一个第三个程序集的类型。
| 归档时间: |
|
| 查看次数: |
1719 次 |
| 最近记录: |