3

我在互联网上搜索了一些,找到了一些关于这个主题的文章,但没有一篇让我满意。我想知道使用对象-对象映射器将对象相互映射好吗?我知道这取决于使用情况,但我将如何实现一个好的或最佳使用情况?

4

2 回答 2

1

退后一步,最佳实践是将数据传输对象 (DTO) 和视图模型 (VM) 与业务对象(实体等)分开。在这方面,映射库是达到目的的一种手段,只是使这种关联更容易。

至于什么时候,这取决于你。如果您觉得可以以一种易于维护的方式在业务模型和 DTO/VM 之间进行转换,请继续。从我个人的经验来看,仅此而已(尤其是随着需求的变化)。因此,我喜欢映射库(特别是 AutoMapper,因为我知道它是 API 并且很乐意将其插入)。

话虽如此,任何时候我必须在这两个模型之间进行转换,我都会使用 AutoMapper。我只需对其进行一次配置,然后就可以开始运行了。对模型(任一侧)的额外调整变得更容易,因为我可以在一个地方(地图定义文件)更改这些绑定,并且方法会自动“赶上”。


例子:

我的数据库包含产品的记录:

class Product
{
    public int Id { get; set; }

    public string Description { get; set; }
    public string Name { get; set; }
    public double Price { get; set; }
    public int QuantityOnHand { get; set; }
    public int? ReorderQuantity { get; set; }
    public string Sku { get; set; }
}

我可能会以更精炼的格式将其呈现给 UI:

public class ProductViewModel
{
    public int Id { get; set; }

    public string Description { get; set; }
    public string Name { get; set; }
    public double Price { get; set; }
    public int Quantity { get; set; }
}

如果这来自某种存储库,我只是调用:

var model = Mapper.Map<ProductViewModel>(productFromRepository)

在这里,我始终从我请求的产品中获得我关心的视图模型。如果业务/服务层要添加/更改/删除属性,我只会回到我的Mapper.CreateMap<Product, ProductViewModel>()定义,但我的表示逻辑的其余部分将保持不变。

于 2015-05-17T14:26:31.267 回答
1

除了@Brad Christie 的回答之外,如果您打算将它们与以不同方式生成的其他产品一起显示在您的视图上,那么将具有微小差异的类型自动映射到单个总体类型通常会更容易。

如果你允许我抄袭我自己以前的答案,这里有一个例子:

class SingleProduct {
    string Name {get;set;}
    decimal Price {get;set;}
    decimal GetActualPrice() { return Price; }
}
class ComboSaleProduct {
    string Name {get;set;}
    List<SingleProduct> ComboProducts {get;set;}
    decimal GetActualPrice() { return ComboProducts.Sum(p => p.GetActualPrice()); }
}

class ProductViewModel {
    string Name {get;set;}
    decimal ActualPrice {get;set;}
}

Automapper 将所有内容连接在一起,以便您可以返回其中任何一个,它会自动将“GetActualPrice”映射到您的视图模型上的 ActualPrice。

于 2015-05-17T15:26:11.047 回答