.net设计模式之装饰模式(Decorator)

当我们需要在不改变原有类的情况下对其进行新功能添加或修改时,装饰模式是一种适用的设计模式。它允许向一个现有对象添加新的功能,同时又不改变其结构。该模式是一种结构性模式。

装饰模式(Decorator)的基本结构

装饰模式有四个角色:

  • 抽象构建(Component):定义一个对象接口,可以给这些对象动态地添加职责。
  • 具体构建(ConcreteComponent):定义一个具体对象,实现抽象构建接口。
  • 装饰(Decorator):持有一个构件对象的实例,并定义一个与抽象构件接口一致的接口。
  • 具体装饰(ConcreteDecorator):向组件添加新的职责。

以大杯奶茶为例的装饰模式

下面我们来使用大杯奶茶为例进行装饰,这里我们定义一个抽象构建 - 饮料(Beverage),它有一个计算价格的方法。

public abstract class Beverage
{
    public abstract double Cost();
}

而具体构建是在抽象构建之上实现的,下面我们定义一种具体构建 - 大杯奶茶(LargeMilkTea),它通过继承饮料来实现其自身的功能:

public class LargeMilkTea : Beverage
{
    public override double Cost()
    {
        return 10.0;
    }
}

现在,如果我们需要给大杯奶茶添加一份珍珠的话,可以使用装饰模式来实现,我们定义一个装饰 - 珍珠(Pearl),它持有一个饮料对象,并且也实现了计算价格的方法,但是它还增加了一份珍珠的花费:

public class Pearl : Beverage
{
    public Beverage Beverage { get; set; }

    public Pearl(Beverage beverage)
    {
        Beverage = beverage;
    }

    public override double Cost()
    {
        return Beverage.Cost() + 3.0;
    }
}

最后,我们可以使用以下代码创建一个大杯奶茶并加上一份珍珠:

Beverage milkTea = new LargeMilkTea();
milkTea = new Pearl(milkTea);

Console.WriteLine("花费:" + milkTea.Cost().ToString());

以数字为例子的装饰模式

下面,我们再以数字为例进行一个装饰,我们定义一个抽象构建 - 数字(Number),它有一个获取数字值的方法。

public abstract class Number
{
    public abstract int GetValue();
}

而具体构建是在抽象构建之上实现的,下面我们定义一种具体构建 - 十进制数(DecimalNumber),它实现了数字的功能:

public class DecimalNumber : Number
{
    private int value;

    public DecimalNumber(int value)
    {
        this.value = value;
    }

    public override int GetValue()
    {
        return value;
    }
}

现在我们定义一个装饰 - 减一(MinusOne),它持有一个数字对象,并且也实现了获取数字值的方法,但是它返回的值减一:

public class MinusOne : Number
{
    public Number Number { get; set; }

    public MinusOne(Number number)
    {
        Number = number;
    }

    public override int GetValue()
    {
        return Number.GetValue() - 1;
    }
}

最后,我们可以使用以下代码创建一个数字对象并减一:

Number number = new DecimalNumber(10);
number = new MinusOne(number);

Console.WriteLine("值:" + number.GetValue().ToString());

以上两个例子均为装饰模式的经典示例,它们展示了装饰模式能如何在已有对象中添加新功能而不改变其结构。

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:.net设计模式之装饰模式(Decorator) - Python技术站

(0)
上一篇 2023年6月3日
下一篇 2023年6月3日

相关文章

  • C#中哈希表(Hashtable)的介绍及简单用法

    C#中的哈希表(Hashtable)是一种集合类型,其存储方式是以键值对(Key-Value pair)的形式存储数据,键和值可以是任意类型。哈希表类似于字典,通过键来查找对应的值。 哈希表(Hashtable)的介绍 哈希表(Hashtable)是.NET Framework提供的一种强类型非泛型集合类型,它实现了IDictionary接口并使用键值对存储…

    C# 2023年6月3日
    00
  • WPF的数据绑定详细介绍

    WPF的数据绑定是WPF框架中的一个重要功能,它能够帮助我们将数据与界面进行绑定,使数据的变化自动反映在界面上。下面,我会给出关于数据绑定的详细介绍,包括数据绑定的意义、数据绑定的实现方式、数据绑定的语法等。同时,还会通过两个示例来说明数据绑定的应用。 1. 数据绑定的意义 在传统的Windows应用中,数据更新通常都是手动进行的,这样就需要在代码中写入大量…

    C# 2023年5月31日
    00
  • 微信开发 网页授权获取用户基本信息

    微信开发中,网页授权是指通过微信公众号或开放平台授权,获取用户在微信中的基本信息,包括昵称、头像、性别、地区等。本文将详细介绍微信开发中网页授权获取用户基本信息的完整攻略,包括授权流程、代码实现和注意事项等。 授权流程 网页授权获取用户基本信息的流程如下: 用户进入网页,点击授权按钮,跳转到微信授权页面。 用户在微信授权页面中确认授权,同意授权后,微信将用户…

    C# 2023年5月15日
    00
  • C#获取DataTable对象状态DataRowState

    获取DataTable对象状态DataRowState攻略 在C#中,DataTable(数据表)是常用的数据存储和处理方式。在使用DataTable的过程中,需要了解DataTable对象的状态DataRowState,以进行数据操作。 1. DataTable对象的状态DataRowState 在DataTable的数据处理中,每个DataRow(行)都…

    C# 2023年5月15日
    00
  • WPF实现绘制3D图形的示例代码

    下面我将为你讲解WPF实现绘制3D图形的完整攻略。 步骤一:引入命名空间 在使用3D图像前,必须引用System.Windows.Media.Media3D和System.Windows.Media.Imaging命名空间,使用如下代码: using System.Windows.Media.Media3D; using System.Windows.Med…

    C# 2023年6月7日
    00
  • 关于C# 4.0新特性“缺省参数”的实现详解

    C# 4.0 新特性:缺省参数 什么是缺省参数? 缺省参数(default parameter)是指在声明方法时,可以给方法的参数设置默认值,这样在调用方法时如果调用者没有为参数传入特定的值,就会使用参数的默认值。缺省参数使得编写方法时更加方便,简化了方法调用者的代码。 如何实现缺省参数? 在 C# 4.0 中,我们可以在声明方法时使用“=值”的方式来给方法…

    C# 2023年5月14日
    00
  • 鼠标右击事件代码(asp.net后台)

    鼠标右击事件是指用户在网页中使用鼠标右键时,触发的相关事件。在ASP.NET后台中,我们可以使用C#或VB.NET编写代码来处理鼠标右击事件。下面是一些详细的攻略和示例: 在页面中注册鼠标右击事件 我们可以通过JavaScript代码,在页面启动时注册鼠标右击事件,代码如下: <script type="text/javascript&quo…

    C# 2023年5月31日
    00
  • 在Asp.net core中实现websocket通信

    在ASP.NET Core中实现WebSocket通信,可以采用ASP.NET Core中自带的WebSocket API或者使用第三方库SignalR进行实现。以下是基于ASP.NET Core原生WebSocket API实现的步骤: 使用WebSocket API实现WebSocket通信 第一步:创建一个ASP.NET Core Web应用程序 在V…

    C# 2023年6月3日
    00
合作推广
合作推广
分享本页
返回顶部