oop - 参数对象的构建器模式
问题描述
请原谅我对设计模式的了解不足。
有时方法有很多参数,根据refactoring-guru 文章,引入Parameter Object是重构代码的正确方法。
想象一下当我们有一个服务来处理某种文档的情况。
public class FinancialStatementService : IFinancialStatementService
{
public Document Create(Options input)
{
// creating basic document content and adding optional data below:
if (input.HasAccountNo)
{
// include account number
}
if (input.HasPaymentDetails)
{
// include payment details
}
if (input.HasZeroBalances)
{
// include zero balances
}
if (input.HasTotal)
{
// include total
}
// and then return the document
}
}
public class Options
{
public DateRange DateRange { get; set; }
public bool HasAccountNo { get; set; }
public bool HasPaymentDetails { get; set; }
public bool HasZeroBalances { get; set; }
public bool HasTotal { get; set; }
}
该文件由许多部分组成,有些是可选的。有时我们需要文档包含所有可能的细节。
但是想象一下某个组织不想要某些细节的情况。
理想情况下,我希望有一个类来处理选项创建并具有包含组织名称的方法,例如
public class OptionsCreator
{
// tax officials want to see all possible details
public static Options GetTaxOfficeOptions(DateRange dateRange)
{
return new Options() { HasAccountNo = true, HasPaymentDetails = true, HasZeroBalances = true, HasTotal = true, DateRange = dateRange };
}
// in some other organization they DO NOT NEED zero balances & payment details
public static Options GetSomeOtherOgranizationOptions(DateRange dateRange)
{
return new Options() { HasAccountNo = true, HasTotal = true, DateRange = dateRange };
}
}
但恐怕上面的例子是反模式。
我能想到的另一件事是建造者模式。
Builder Pattern会是Parameter Object的最佳解决方案吗?
解决方案
我通常这样使用:
带 - 的常量类(在本例中,我使用第一个参数作为 xml 解析的字符串,第二个参数作为默认值)
public static readonly Dictionary<string, Tuple<string, object>> fieldNamesWithOptions = new Dictionary<string, Tuple<string, object>>() { { "number", new Tuple<string, object>("PONumber","") }, { "shipDate", new Tuple<string, object>("ShipDate", new DateTime(1900, 1, 1)) }, { "detailID", new Tuple<string, object>("DetailID", -1) }, }
像这样处理你的选项(伪代码,想象元组中的第三个参数正在准备函数):
for every field F in object O:
if(fieldNamesWithOptions.ContainsKey(F.name))
{
result += fieldNamesWithOptions[F].third(O.F);
}
我使用伪代码是因为在 C# 中它看起来相当复杂。
这种重构将清除您的代码,将逻辑拆分成可以理解/测试的小块。另一方面,我们有不寻常的循环for every field F in object O:
,但被调试一次,它可以在项目的任何其他部分的一些帮助器中使用。
推荐阅读
- python - 在 python 中显示 10 个第一个素数斐波那契数
- c - sscanf 和 scanset 停止读取十六进制数字
- python - Creating a GUI for Selenium
- java - How do I solve the error: Failed to load keystore type [PKCS12 ]
- vuejs2 - Vuetify v-data-table drag and resizable columns together
- r - Results from MATLAB's crosscorr function and R's ccf different
- c# - How do I save data in related tables?
- javascript - 使用 discord.js v12 的 rate 命令
- visual-studio - 快照调试:无法从 URL 获得响应
- javascript - OffcanvasMenu 插件 - 点击事件,Shopware 6