让我们假设我们必须创建具有一些预定义(默认值)值的复杂DTO对象。此对象用于序列化,序列化程序需要无参数构造函数。要做到这一点,我想使用静态工厂方法,但我对这种方法的正确使用有一些疑问。
请考虑以下两个例子:
public class Foo
{
public void DoSomething()
{
// the first way of creating the object
var addressDtoFirstWay = AddressDtoFirstWay
.CreateWithPredefinedValues();
addressDtoFirstWay.StreetName = "Street";
addressDtoFirstWay.HouseNumber = 100;
addressDtoFirstWay.PostalCode = "1000";
// the second way of creating the object
var addressDtoSecondWay = AddressDtoSecondWay
.CreateWithPredefinedValues("Street", 100, null, "1000");
}
}
public class AddressDtoFirstWay
{
public string RecipientName { get; set; }
public string StreetName { get; set; }
public int HouseNumber { get; set; }
public int? FlatNumber { get; set; }
public string PostalCode { get; set; }
public string City { get; set; }
public string CountryName { get; set; }
public static AddressDtoFirstWay CreateWithPredefinedValues()
{
return new AddressDtoFirstWay
{
RecipientName = "John Doe",
City = "City",
CountryName = "Country"
};
}
}
public class AddressDtoSecondWay
{
public string RecipientName { get; set; }
public string StreetName { get; set; }
public int HouseNumber { get; set; }
public int? FlatNumber { get; set; }
public string PostalCode { get; set; }
public string City { get; set; }
public string CountryName { get; set; }
public static AddressDtoSecondWay CreateWithPredefinedValues(
string streetName,
int houseNumber,
int? flatNumber,
string postalCode)
{
return new AddressDtoSecondWay
{
RecipientName = "John Doe",
StreetName = streetName,
HouseNumber = houseNumber,
FlatNumber = flatNumber,
PostalCode = postalCode,
City = "City",
CountryName = "Country"
};
}
}
在第一个示例中,工厂方法只初始化预定义的字段--用户必须在创建对象后初始化其余字段。第二个示例初始化预定义字段,也初始化需要的字段,但作为缺点,用户必须填充可空字段(在这种情况下不是必需的,但在另一个字段中是必需的)字段flatNumber
。
我看到了这两种解决方案的优点和缺点,但我正在考虑哪一种更可取,以及为什么。也许其他方法会更好。我愿意接受任何建议,但我想注意的是,这个问题并不复杂,构建器模式将适用于这个问题。
发布于 2019-04-04 18:54:32
假设你
也许解决办法是将两者分开。让你的DTO做它自己的事情:
public class AddressDto
{
public string RecipientName { get; set; }
public string StreetName { get; set; }
public int HouseNumber { get; set; }
public int? FlatNumber { get; set; }
public string PostalCode { get; set; }
public string City { get; set; }
public string CountryName { get; set; }
}
...and不会将其与各种默认选项相混淆。随着时间的推移,您会发现对于不同的场景,您需要不同的缺省值。我能看到这会变得有点混乱。
然后,采取完全相同的静态方法,并将它们放在自己的类中:
public static class AddressDtoFactory
{
public static AddressDto CreateWithPredefinedValues()
{
return new AddressDto
{
RecipientName = "John Doe",
City = "City",
CountryName = "Country"
};
}
}
我倾向于“第一种方式”,其中工厂方法只填充默认值。原因是,必须将每个属性作为参数传递,这有点负担,特别是如果它们没有得到验证。另外,每次添加属性时,都希望更新该构造函数。
另一个选项是这样的扩展类:
public static class AddressDtoExtensions
{
public static AddressDto PopulatePredefinedValues(
this AddressDto dto)
{
dto.RecipientName = dto.RecipientName ?? "John Doe";
dto.City = dto.City ?? "City";
dto.CountryName = dto.CountryName ?? "Country";
return dto;
}
}
这样你就可以做这样的事情:
var dto = new AddressDto
{
HouseNumber = 5,
PostalCode = "12345"
}.PopulatePredefinedValues();
它给了您两个-您可以使用两个属性初始化和添加您的默认值。如果您决定使用Automapper或诸如此类的东西,也可能会更友好一些。
https://stackoverflow.com/questions/55505292
复制相似问题