在不编写大量样板代码的情况下对类进行外观设计? [英] Facade a class without writing lots of boilerplate code?

查看:21
本文介绍了在不编写大量样板代码的情况下对类进行外观设计?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

假设我有一个来自第 3 方的类,它是一个数据模型.它可能有 100 个属性(一些带有公共 setter 和 getter,其他带有公共 getter 但私有 setter).让我们称这个类为 ContosoEmployeeModel

Let's say I have a class from a 3rd-party, which is a data-model. It has perhaps 100 properties (some with public setters and getters, others with public getters but private setters). Let's call this class ContosoEmployeeModel

我想用一个接口(INavigationItem,它具有 Name 和 DBID 属性)为这个类添加外观,以允许它在我的应用程序中使用(它是一个 PowerShell 提供程序,但现在这并不重要).但是,它还需要可用作 ContosoEmployeeModel.

I want to facade this class with an interface (INavigationItem, which has Name and DBID properties) to allow it to be used in my application (it's a PowerShell provider, but that's not important right now). However, it also needs to be usable as a ContosoEmployeeModel.

我最初的实现是这样的:

My initial implementation looked like this:

public class ContosoEmployeeModel
{
    // Note this class is not under my control. I'm supplied
    // an instance of it that I have to work with.

    public DateTime EmployeeDateOfBirth { get; set; }
    // and 99 other properties.
}

public class FacadedEmployeeModel : ContosoEmployeeModel, INavigationItem
{
    private ContosoEmployeeModel model;
    public FacadedEmployeeModel(ContosoEmployeeModel model)
    {
        this.model = model;
    }

    // INavigationItem properties
    string INavigationItem.Name { get; set;}

    int INavigationItem.DBID { get; set;}

    // ContosoEmployeeModel properties
    public DateTime EmployeeDateOfBirth
    {
        get { return this.model.EmployeeDateOfBirth; }
        set { this.model.EmployeeDateOfBirth = value; }
    }
    // And now write 99 more properties that look like this :-(
}

但是,很明显,这将涉及编写大量样板代码来公开所有属性,如果可以,我宁愿避免这种情况.我可以在部分类中 T4 代码生成此代码,如果没有更好的想法,我会这样做,但我虽然我会在这里询问是否有人使用一些 super wizzy 一点 C#魔法

However, it's clear that this will involve writing a huge amount of boilerplate code to expose all the properties , and I'd rather avoid this if I can. I can T4 code-generate this code in a partial class, and will do if there aren't any better ideas, but I though I'd ask here to see if anyone had any better ideas using some super wizzy bit of C# magic

请注意 - 我用来获取 ContosoEmployeeModel 的 API 只能返回 ContosoEmployeeModel - 我无法扩展它以返回 FacededEmployeeModel,所以包装模型是我能想到的唯一解决方案 - 我很高兴虽然更正:)

Please note - the API I use to obtain the ContosoEmployeeModel can only return a ContosoEmployeeModel - I can't extend it to return a FacededEmployeeModel, so wrapping the model is the only solution I can think of - I'm happy to be corrected though :)

推荐答案

另一种可能适合您的方法是使用 AutoMapper 将基类映射到您的外观,这里是示例代码:

The other approach may be suitable for you is to use AutoMapper to map base class to your facade here is sample code:

class Program
    {
        static void Main(string[] args)
        {
            var model = new Model { Count = 123, Date = DateTime.Now, Name = "Some name" };

            Mapper.CreateMap<Model, FacadeForModel>();
            var mappedObject = AutoMapper.Mapper.Map<FacadeForModel>(model);

            Console.WriteLine(mappedObject);

            Console.ReadLine();
        }

        class Model
        {
            public string Name { get; set; }

            public DateTime Date { get; set; }

            public int Count { get; set; }
        }

        interface INavigationItem
        {
            int Id { get; set; }

            string OtherProp { get; set; }
        }

        class FacadeForModel : Model, INavigationItem
        {
            public int Id { get; set; }

            public string OtherProp { get; set; }
        }
    }

这篇关于在不编写大量样板代码的情况下对类进行外观设计?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆