手撸golang 结构型设计模式 适配器模式

.container .card .information strong · · 553 次点击 · · 开始浏览    
这是一个创建于 的文章,其中的信息可能已经有所发展或是发生改变。

手撸golang 结构型设计模式 适配器模式

缘起

最近复习设计模式
拜读谭勇德的<<设计模式就该这样学>>
本系列笔记拟采用golang练习之

适配器模式

适配器模式(Adapter Pattern)又叫作变压器模式,它的功能是将一个类的接口变成客户端所期望的另一种接口,从而使原本因接口不匹配而导致无法在一起工作的两个类能够一起工作,属于结构型设计模式。
_

场景

  • 某智能家居应用, 可接入并显示温度计信息
  • 系统设计的温度计接口, 采用的是摄氏度单位
  • 现按客户需求, 要接入某进口款温度计, 厂家提供的sdk只提供华氏度的温度信息
  • 根据适配器模式, 在不修改系统原有接口的情况下, 兼容新设备接入
  • 华氏度 = 32+ 摄氏度 × 1.8, 摄氏度 = (华氏度 - 32) ÷ 1.8

设计

  • IThermometer: 现有系统的温度计接口, 温度单位为摄氏度. 本次更新希望保持接口不变, 以免影响现有系统.
  • IThermometerFactory: 现有系统的温度计工厂接口. 本次更新希望保持接口不变, 以免影响现有系统.
  • ISpecialThermometer: 厂家sdk提供的温度计接口, 温度单位为华氏度
  • tMockSpecialThermometer: 厂家sdk提供的温度计实现
  • tMockSpecialAdapter: 根据适配器模式, 实现的温度计适配器, 为新温度计适配现有系统的接口
  • tMockSpecialFactory: 新温度计的工厂类, 实现IThermometerFactory接口

单元测试

adapter_pattern_test.go

package structural_patterns

import (
    "learning/gooop/structural_patterns/adapter"
    "testing"
)

func Test_AdapterPattern(t *testing.T) {
    factory := adapter.SpecialThermometerFactory
    thermometer := factory.Create("This is some configuration")
    t.Logf("centigrade = %v", thermometer.Centigrade())
}

测试输出

$ go test -v adapter_pattern_test.go 
=== RUN   Test_AdapterPattern
    adapter_pattern_test.go:11: centigrade = 26.5
--- PASS: Test_AdapterPattern (0.00s)
PASS
ok      command-line-arguments  0.003s

IThermometer.go

现有系统的温度计接口, 温度单位为摄氏度.

package adapter

// 现有系统的温度计接口, 摄氏度
type IThermometer interface {
    Centigrade() float64
}

IThermometerFactory.go

现有系统的温度计工厂接口.

package adapter

type IThermometerFactory interface {
    Create(config string) IThermometer
}

ISpecialThermometer.go

厂家sdk提供的温度计接口, 温度单位为华氏度

package adapter

// 新接入的温度计, 华氏度
type ISpecialThermometer interface {
    Fahrenheit() float64
}

tMockSpecialThermometer.go

厂家sdk提供的温度计实现

package adapter

type tMockSpecialThermometer struct {
    mAddress string
}

func newMockSpecialThermometer(address string) ISpecialThermometer {
    return &tMockSpecialThermometer{
        address,
    }
}

func (me *tMockSpecialThermometer) Fahrenheit() float64 {
    return 79.7
}

tMockSpecialAdapter.go

根据适配器模式, 实现的温度计适配器, 为新温度计适配现有系统的接口

package adapter

type tMockSpecialAdapter struct {
    mOrigin ISpecialThermometer
}


func newSpecialAdapter(origin ISpecialThermometer) IThermometer {
    return &tMockSpecialAdapter{
        origin,
    }
}

func (me *tMockSpecialAdapter) Centigrade() float64 {
    return (me.mOrigin.Fahrenheit() - 32) * 5 / 9
}

tMockSpecialFactory.go

新温度计的工厂类, 实现IThermometerFactory接口

package adapter

type tMockSpecialFactory struct {
}

func newMockSpecialFactory() IThermometerFactory {
    return &tMockSpecialFactory{}
}

func (me *tMockSpecialFactory) Create(config string) IThermometer {
    t := newMockSpecialThermometer(me.parseAddress(config))
    return newSpecialAdapter(t)
}

func (me *tMockSpecialFactory) parseAddress(config string) string {
    return "http://localhost:8080"
}


var SpecialThermometerFactory IThermometerFactory = newMockSpecialFactory()

适配器模式小结

适配器模式的优点
(1)能提高类的透明性和复用,但现有的类复用不需要改变。
(2)适配器类和原角色类解耦,提高程序的扩展性。
(3)在很多业务场景中符合开闭原则。
适配器模式的缺点
(1)适配器编写过程需要结合业务场景全面考虑,可能会增加系统的复杂性。
(2)增加代码阅读难度,降低代码可读性,过多使用适配器会使系统代码变得凌乱。
_
(end)


有疑问加站长微信联系(非本文作者)

本文来自:Segmentfault

感谢作者:.container .card .information strong

查看原文:手撸golang 结构型设计模式 适配器模式

入群交流(和以上内容无关):加入Go大咖交流群,或添加微信:liuxiaoyan-s 备注:入群;或加QQ群:692541889

553 次点击  
加入收藏 微博
添加一条新回复 (您需要 登录 后才能回复 没有账号 ?)
  • 请尽量让自己的回复能够对别人有帮助
  • 支持 Markdown 格式, **粗体**、~~删除线~~、`单行代码`
  • 支持 @ 本站用户;支持表情(输入 : 提示),见 Emoji cheat sheet
  • 图片支持拖拽、截图粘贴等方式上传