gpt4 book ai didi

c# - 是否可以在 C# 中简化嵌套泛型?

转载 作者:太空狗 更新时间:2023-10-29 21:57:00 29 4
gpt4 key购买 nike

我喜欢 C# 中的泛型,但有时使用它们会变得有点复杂。我时不时遇到下面的问题。有没有办法让这个场景更简单?我看不出怎么做,但我希望有人可以:)

给定三个基类:

public abstract class Inner
{
}

public abstract class Outer<T>
where T : Inner
{
}

public abstract class Handler<TOuter, TInner>
where TOuter : Outer<TInner>
where TInner : Inner
{
public abstract void SetValue(TInner value);
}

以及一些简单的实现:

public class In : Inner
{
}

public class Out : Outer<In>
{
}

public class HandleOut : Handler<Out, In>
{
public override void SetValue(In value) { }
}

现在我的问题是:HandleOut , TInner 的类型由“Out”类型给出,所以有什么方法可以简化 HandleOut 的定义吗?类似于 public class HandleOut : Handler<Out>并且仍然能够使用内部类型作为 SetValue 的参数?

这是一个非常简单的示例,但有时我会在定义中得到一长串泛型类型,而通常所有泛型类型都可以从第一种类型中逻辑推导出来。有没有我遗漏的技巧?

最佳答案

没有。

虽然这样的推论应该是可能的,但它不是语言的一部分。您可能有兴趣向 Roslyn 提出这个建议(打开一个新问题)。当然,这种类型的通用约束推断在复杂的情况下可能会遇到问题,但至少对于简单的情况来说它是可行的......不过,C# 团队应该把时间和精力花在哪里?

Why are generic constraints not inherited Damien_The_Unbeliever 所在的链接 shared on the comments


无论如何,在您提供的代码中,虽然 Out 确实已经为您提供了 In 类型,但不需要通用参数 TOuter

下面的代码同样有效:

public abstract class Inner
{
}

public abstract class Outer<T>
where T : Inner
{
}

public abstract class Handler<TInner> // NOTE: TOuter removed
where TInner : Inner
{
public abstract void SetValue(TInner value);
}

public class In : Inner
{
}

public class Out : Outer<In>
{
}

public class HandleOut : Handler<In> // NOTE: Out removed
{
public override void SetValue(In value) { }
}

因此,如果需要,可以考虑使用 Outer<TInner> 而不是 TOuter。当然,如果您保留一个 TOuter 列表,那么它的限制就会减少,因为它将允许任何派生类型的 Outer<TInner> 而不是任何派生类型的 TOuter

因为您没有在通用约束中放置“new”,所以您不是在创建这种类型的对象,但如果出现这种情况,您可以在构造函数中接受 Func<Outer<TInner>>

关于c# - 是否可以在 C# 中简化嵌套泛型?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34505669/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com