通用方法的多个(OR)类型的约束通用方法的多个(OR)类型的约束(Generic method mu

2019-05-16 19:14发布

读此 ,我了解到这是可以允许的方法通过使一个通用的方法来接受多种类型的参数。 在该实例中,下面的代码与一类约束用于确保“U”是IEnumerable<T>

public T DoSomething<U, T>(U arg) where U : IEnumerable<T>
{
    return arg.First();
}

我发现一些这使得添加多个类型约束,如更多的代码:

public void test<T>(string a, T arg) where T: ParentClass, ChildClass 
{
    //do something
}

然而,这种代码出现强制实施该arg必须既是一个类型的ParentClass ChildClass 。 我想要做的是说,ARG可能是一个类型的ParentClass ChildClass以下方式:

public void test<T>(string a, T arg) where T: string OR Exception
{
//do something
}

您的帮助表示赞赏一如既往!

Answer 1:

这是不可能的。 你可以,但是,定义特定类型的重载:

public void test(string a, string arg);
public void test(string a, Exception arg);

如果这些是一个通用类的一部分,它们将在该方法的通用版本是优选的。



Answer 2:

Botz答案是100%正确的,这里有一个简短的说明:

当你写一个方法(通用与否),并宣布该类型的方法需要你定义一个合同的参数:

如果你给我知道怎么做的那套东西T型知道怎么做,我可以提供是“A”的对象:一个回报,我声明类型的值,或“B”:某种行为的使用该类型。

如果你试图给它不止一种类型在一个时间(由具有或),或设法得到它返回,可能是多种类型的该合同得到模糊的值:

如果你给我一个知道如何跳绳或知道如何计算圆周率到第15位,我会要么返回一个对象,可以去钓鱼或可能预拌混凝土的对象。

问题是,当你进入的方法,你不知道,如果他们给你一个IJumpRopePiFactory 。 此外,当你继续使用的方法(假设你得到它的神奇编译)你真的不知道,如果你有一个FisherAbstractConcreteMixer 。 基本上,它使整个事情的方式更加混乱。

你的问题的解决方案是二possiblities之一:

  1. 定义定义每个可能的转换,行为,或任何一种以上的方法。 这是Botz的答案。 在编程世界中,这被称为重载方法。

  2. 定义知道怎么做所有你需要的方法,并有一个方法的事情需要只是类型的基类或接口。 这可能涉及结束了一个stringException的小类来定义它们映射到落实你怎么打算,但后来一切都超清晰易读。 我能来,再过4年,读你的代码,并很容易理解这是怎么回事。

你的选择取决于如何复杂选择1和2是如何扩展它需要。

因此,对于您的具体情况我会想象你刚刚拉出来自异常的消息或东西:

public interface IHasMessage
{
    string GetMessage();
}

public void test(string a, IHasMessage arg)
{
    //Use message
}

现在,所有你需要的是改变一个方法stringException到IHasMessage。 很容易。



Answer 3:

如果ChildClass意味着它是从父类派生,你可以像下面同时接受父类和ChildClass;

public void test<T>(string a, T arg) where T: ParentClass 
{
    //do something
}

在otherhand,如果你想使用两种不同类型之间没有继承关系,你应该考虑实现相同的接口类型;

public interface ICommonInterface
{
    string SomeCommonProperty { get; set; }
}

public class AA : ICommonInterface
{
    public string SomeCommonProperty
    {
        get;set;
    }
}

public class BB : ICommonInterface
{
    public string SomeCommonProperty
    {
        get;
        set;
    }
}

那么你可以为你写泛型函数;

public void Test<T>(string a, T arg) where T : ICommonInterface
{
    //do something
}


文章来源: Generic method multiple (OR) type constraint