我最近发现自己在我的代码中一遍又一遍地使用相同的模式。基本上,它是访问者模式的一种变体,我使用它来将对基类实例的引用解析为派生实例。这种方法需要大量样板代码。
问题:
- 如何在不编写大量访问者代码的情况下以静态/严格类型的方式在 C# 中多分派一个方法?
- 是否有生成此代码的工具/扩展?
- 为什么 C# 语言中没有解决多分派的问题?我不相信我是唯一一个觉得这很烦人的人。我可能大错特错,问题不存在,所以我想知道你是如何处理它的。
我最近发现自己在我的代码中一遍又一遍地使用相同的模式。基本上,它是访问者模式的一种变体,我使用它来将对基类实例的引用解析为派生实例。这种方法需要大量样板代码。
问题:
如何在不编写大量访问者代码的情况下以静态/严格类型的方式在 C# 中多分派方法?
我不知道有任何技术。
在用 C# 编写的 C# 编译器的 Roslyn 版本中,我们在具有数十或数百个成员的类型层次结构上到处使用访问者模式。我们编写了一个实用程序,它将类型的 XML 描述转换为类型的声明以及访问者的基类。这对我们来说似乎工作得很好。
是否有生成此代码的工具/扩展?
有; 我们自己写的。这并不难。你也可以做到的。
为什么 C# 作为一门语言没有任何东西可以解决多调度问题?
我们有一个可能比你的手臂更长的语言特征列表。任何给定的版本,我们都有预算做两到三个,最重要的是,因此我们专注于获得最大可能的收益。
通过自动生成访问者模式更容易实现双重(或多重)虚拟调度从来没有使它接近该列表的顶部。从字面上看,我们可以在语言中嵌入许多其他可能的模式,这些模式更“物有所值”。如果您对流行语言进行调查,您会发现很少有语言通过静态分析支持双重或多重虚拟调度,而那些支持的语言也不是很受欢迎。这是有原因的:首先,因为它实际上并不是一个非常有用的功能,其次,因为当您确实需要它时,您可以通过自己实现模式或使用动态调度来实现它。
正如您所注意到的,基于模式的方法和动态调度方法都存在明显的缺点。但是,尽管有缺点,但对于普通的业务线开发人员来说,如果他们需要的话,它们都是可行的。在评估要在语言中嵌入哪些模式时,我们倾向于那些对于普通开发人员来说非常难以使用基于模式的方法实现自己的模式。访客模式并不难;这很冗长。
例如:在 C# 2 中,我们选择在语言中嵌入“序列生成器”模式。在 C# 3 中,我们选择在语言中嵌入“带有序列单子的查询理解”模式。在 C# 4 中,我们选择在语言中嵌入“动态调度”模式。在 C# 5 中,我们选择将“将当前延续作为委托传递”模式嵌入到语言中。所有这些都是“物有所值”的例子——它们的实现成本很高,但它们从根本上使新的编程风格在核心语言中可用。
任何版本都只有有限的工作量;在一个版本的语言中嵌入一种模式会阻止我们在该版本的语言中嵌入任何其他模式,因为根本没有预算去做。
当将“双重(或多重)虚拟调度”模式嵌入到语言中成为花费我们预算的最佳方式时,我们会这样做,而不是之前。因此,您应该等待很长时间。