具有多个约束条件的通用方法

331

我有一个通用方法,其中包含两个通用参数。我尝试编译下面的代码,但它不能工作。这是.NET的限制吗?是否可能为不同的参数设置多个约束条件?

public TResponse Call<TResponse, TRequest>(TRequest request)
  where TRequest : MyClass, TResponse : MyOtherClass
4个回答

519

这是可能的,您只是语法有些错误。 您需要为每个约束条件使用where关键字来定义,而不是用逗号分隔它们:

public TResponse Call<TResponse, TRequest>(TRequest request)
    where TRequest : MyClass
    where TResponse : MyOtherClass

8
你能否在同一泛型上设置多个约束条件,例如 where T : MyClass where T : MyOtherClass - WDUK
1
@WDUK 有点像。C#不允许多重继承。然而,你可以指定一些接口和其他特殊条件,以及单个类。每个要求都用逗号分隔(这也是为什么Martin的尝试不是有效的C#:在那种情况下,逗号已经有了其他的含义)。所以,where T : MyClass, IMyInterface是有效的,但where T : MyClass, MyOtherClass是无效的。 - undefined

24

除了@LukeH的主要答案中提到的其他用法外,我们可以使用多个接口而不是类(一个类和n个接口)像这样

public TResponse Call<TResponse, TRequest>(TRequest request)
  where TRequest : MyClass, IMyOtherClass, IMyAnotherClass
或者
public TResponse Call<TResponse, TRequest>(TRequest request)
  where TRequest : IMyClass,IMyOtherClass

12

除了@LukeH的主要答案之外,我还有依赖注入的问题,花费了我一些时间来修复。值得分享给那些遇到同样问题的人:

public interface IBaseSupervisor<TEntity, TViewModel> 
    where TEntity : class
    where TViewModel : class

这是解决方法。在容器/服务中,关键是typeof和逗号(,)

services.AddScoped(typeof(IBaseSupervisor<,>), typeof(BaseSupervisor<,>));

这在这个答案中提到了。


2
这个答案与类型约束无关,而是关于未绑定的泛型类型以及如何在C#中拼写它们。https://dev59.com/vXI95IYBdhLWcg3wvwoQ#2173115 https://dev59.com/QGw15IYBdhLWcg3wcbay#6607299 - Palec

6
每个限制条件都需要独立成一行,如果有多个限制条件适用于单个泛型参数,则它们需要用逗号分隔。
public TResponse Call<TResponse, TRequest>(TRequest request)
    where TRequest : MyClass 
    where TResponse : MyOtherClass, IOtherClass

根据评论进行编辑


这个答案是不正确的,无论是 MyClass 后面的逗号(请参见得票最高的答案),还是声称约束需要在单独的行上。我会修复它,但编辑队列已满。 - Todd West
感谢@ToddWest。我已经删除了MyClass后面的额外逗号。 - mybrave

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接