gpt4 book ai didi

c# - 简单类+工厂的通用解决方案

转载 作者:行者123 更新时间:2023-11-30 17:21:53 25 4
gpt4 key购买 nike

我的小脑袋无法想出一个优雅的解决方案来解决这个问题。假设我有这样的类(class):

    public class Foo<T>
{
public RecordType Type { get; set; }
public T Value { get; set; }
}

在哪里RecordType可能看起来像这样:

 public enum RecordType
{
EmptyRecord,
BooleanRecord,
IntegerRecord,
StringRecord,
ByteRecord
}

目标是治疗 IEnumerable<Foo<T>>统一进行迭代和/或打开 RecordType并执行一个 Action ,同时尽可能避免装箱内在类型。另外,最好使用工厂来创建这些 Foo脱离了工厂方法。

我在基类或接口(interface)中尝试了一些通用性的快速实现,但我想出的任何东西都无法优雅地回答这个看似非常简单的问题。

小修改:我应该提到我的主要目标是使用 .Value 而不强制对调用者进行转换。

最佳答案

您可以引入一个非泛型接口(interface) IFoo:

public interface IFoo
{
RecordType Type { get; set; }
}

由通用 Foo 类实现:

public class Foo<T> : IFoo
{
public T Value { get; set; }
}

并创建一个根据 RecordType 创建 Foo 实例的工厂方法:

public static IFoo CreateFoo(RecordType type)
{
switch (type)
{
case RecordType.Bool: return new Foo<bool>();
// ...
}
}

一旦您以这种方式创建了一个 Foo 实例,您还不能访问该值,因为您还不知道类型参数。但是您可以使用 Type 属性检查类型并进行适当的转换:

IFoo foo = CreateFoo(RecordType.Bool);

if (foo.Type == RecordType.Bool)
{
Foo<bool> boolFoo = (Foo<bool>)foo;
bool value = boolFoo.Value;
}

如果您有一个适用于 Foo 对象的方法,例如:

void DoIt<T>(IEnumerable<Foo<T>> foos)
{
foreach (Foo<T> foo in foos)
{
Qux(foo.Value);
}
}

并且有一个可枚举的 IFoo 对象,你可以 Cast/OfType :

IEnumerable<IFoo> foos = // ...
DoIt<bool>(foos.OfType<Foo<bool>>());

因此,从本质上讲,如果您在编译时知道 T,则使用 Foo ,如果您仅在运行时知道 T,则使用 IFoo。 IFoo 需要检查以在运行时将其转换为某个 T 的 Foo

关于c# - 简单类+工厂的通用解决方案,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3133354/

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