C# 为泛型方法调用错误的重载

C# 为泛型方法调用错误的重载,c#,generics,extension-methods,C#,Generics,Extension Methods,我有两个非常相似的通用方法。其思想是,一个可以用显式返回类型调用,而另一个则推断返回类型与提供的obj相同 第一个方法的调用方式如下:response response=myCat.Put() 现在我可以看出,这些定义与Respect之间是多么的模棱两可。奇怪的是没有编译错误,但是在运行时,我得到了一个堆栈溢出,因为第二个方法只是调用自己 有没有一种方法可以让第二个方法调用第一个方法而不更改任何一个方法的名称?在决定两个方法的“更好性”时(这是当一个方法调用匹配多个签名时所做的),首选定义为“更

我有两个非常相似的通用方法。其思想是,一个可以用显式返回类型调用,而另一个则推断返回类型与提供的
obj
相同

第一个方法的调用方式如下:
response response=myCat.Put()

现在我可以看出,这些定义与Respect之间是多么的模棱两可。奇怪的是没有编译错误,但是在运行时,我得到了一个堆栈溢出,因为第二个方法只是调用自己

有没有一种方法可以让第二个方法调用第一个方法而不更改任何一个方法的名称?

在决定两个方法的“更好性”时(这是当一个方法调用匹配多个签名时所做的),首选定义为“更接近”调用点的方法

两个更常见的例子:

  • 如果一个方法是在同一类型中定义的,而另一个不是,则该类型中的方法获胜

  • 如果一个方法在同一个命名空间中,而另一个不在,则同一命名空间中的方法获胜

  • 解决歧义的一种方法是不利用它是一种扩展方法这一事实;调用它,就好像它不是一样(不过它仍然可以是一个扩展方法,供外部调用方使用)

    public static O Put(此O对象,列表参数=null)
    何处O:APIResource
    {返回OtherPutClass.Put(obj,参数);}
    
    您是否尝试显式强制转换为正确的类型

    似乎是这样的:

    public static O Put<out O>( this O obj , List<Parameter> parameters = null ) where O:APIResource
    {
      return ((APIResource)obj).Put<O>(parameters) ;  //I want to call the first method here.
    }
    
    publicstatico-Put(这个O-obj,List-parameters=null),其中O:apirource
    {
    return((APIResource)obj.Put(parameters);//我想在这里调用第一个方法。
    }
    

    publicstatico-Put(这个O-obj,List-parameters=null),其中O:apirource
    {
    return.Put((APIResource)obj,parameters);//我想在这里调用第一个方法。
    }
    
    我们给你想要的


    然而,类型系统与您的意图相混淆这一事实可能表明,试图修复一个bug的人也会感到困惑。

    这是一个好主意,但他们都属于同一类。这是否需要在自己的类中创建包装每个扩展方法?如果您显式地将
    obj
    转换为
    APIResource
    ,它可能会调用第一个方法。@Alain这当然是一个选项。也就是说,我不认为第一种方法有任何理由;只需将该实现放在第二个方法中,该方法可以处理第一个方法可以处理的所有情况以及更多情况。@RobSiklos nope,这样做不行(只是测试它以确定)。@Servy我的问题是,如果我只有后者,那么用户将始终必须指定该方法的返回类型。由于该方法最常用的用法就是说
    MyObject.Post()
    ,所以我想确保它的使用简单明了。要求用户键入
    MyObject.Post()在这种情况下似乎不必要地复杂。只需一点更正:应该调用哪个方法是由编译器决定的,而不是糟糕的Visual Studio:)@Servy Good eye!我正在试验某个东西,但忘了移除它。不,这无法修复它;事实上,这只会导致编译时错误,因为现在“最佳”匹配方法没有兼容的参数列表。
    
    //<typeparam name="O">(Automatically Inferred) The type of the current resource, which is also the expected type of the resource request response.</typeparam>
    public static O Put<O>(this O obj, List<Parameter> parameters = null) 
         where O : APIResource 
    { return obj.Put<O>(parameters); } //I want to call the first method here.
    
    public static O Put<O>(this O obj, List<Parameter> parameters = null) 
         where O : APIResource 
    { return OtherPutClass.Put<O>(obj, parameters); }
    
    public static O Put<out O>( this O obj , List<Parameter> parameters = null ) where O:APIResource
    {
      return ((APIResource)obj).Put<O>(parameters) ;  //I want to call the first method here.
    }
    
    public static O Put<out O>( this O obj , List<Parameter> parameters = null ) where O:APIResource
    {
      return .Put<O>( (APIResource)obj , parameters) ;  //I want to call the first method here.
    }