gpt4 book ai didi

c# - 确定在运行时使用哪个类

转载 作者:太空狗 更新时间:2023-10-30 01:24:33 25 4
gpt4 key购买 nike

我正在处理看起来与此非常相似的遗留代码:

public class BaseParser
{
public BaseParser(Stream stream)
{
// Do something with stream
}
}

public class JsonParser : BaseParser
{
public JsonParser(Stream stream)
: base(stream)
{
// Do something
}
}

public class XmlParser : BaseParser
{
public XmlParser(Stream stream, string someOtherParam)
: base(stream)
{
// Do something
}
}

我们有一个使用特定解析器解析传入文件的应用程序。为了确定我们需要实例化哪种类型,工厂方法中有一个很大的 IF/ELSE block :

public static BaseParser Create(string type)
{
if (type == "xml")
return new XmlParser(new FileStream("path", FileMode.Open), "test");

if (type == "json")
return new JsonParser(new FileStream("path", FileMode.Open));

// more...

return null;
}

由于单个程序集中有大量解析器(我们称之为 Demo.dll ),我想将这些解析器中的每一个拆分成它们自己的程序集。 “核心”类,例如 BaseParser将留在 Demo.dll ,但其他解析器和任何依赖项将存在于 Demo.Json.dll 中, Demo.Xml.dll等等……

“核心”库将在运行时加载这些程序集。

string[] paths = Directory.GetFiles(Environment.CurrentDirectory, "Demo.*.dll");

foreach (string path in paths)
Assembly.LoadFrom(path);

List<BaseParser> parsers = AppDomain.CurrentDomain
.GetAssemblies()
.SelectMany(x => x.GetTypes())
.Where(x => x.IsSubclassOf(typeof(BaseParser)))
.Select(x => (BaseParser) Activator.CreateInstance(x))
.ToList();

问题从这里开始。上面的代码将不起作用,因为每个遗留解析器都没有无参数构造函数。另外,我想不出一个好的方法来替换 IF/ELSE block 并让每个解析器确定它可以处理哪个文件。我正在考虑可能在基础解析器上添加一个虚拟方法:

public virtual bool ShouldHandle(string type)
{
return false;
}

... 并且每个派生的解析器都将覆盖此虚拟方法。但是,有两个问题:

  1. 没有无参数的构造函数,每个类的构造函数可以有不同数量的参数。这不是我可以更改的,因为到处都在使用这些遗留类。

  2. 我必须先实例化类,然后才能调用 ShouldHandle方法。这给在构造函数中从流中读取的类带来了问题。

是否有其他方法可以将这些解析器拆分成它们自己的程序集?

编辑:

这是一个 .NET 3.5 应用程序。不幸的是没有 MEF。

最佳答案

我发现在这些情况下使用抽象工厂类会有所帮助。

每个程序集都有一个专门用于创建驻留在该程序集中的类的工厂。

实际上,您随后让一个工厂创建了一个具体工厂,以便创建您的具体解析器。

通过这种方式,您还可以将逻辑放在适当的位置,从而在尝试创建与其关联的具体工厂之前检查程序集是否存在。

我知道它没有绕过 if else 结构(尽管可以用 switch 代替,为每个类传递一个参数,但它确实允许您将其分解并使其更易于处理和支持。

关于c# - 确定在运行时使用哪个类,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8922996/

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