第四天:创建型模式--原型模式

news/2024/7/24 11:27:39

####零、原型模式

  • 什么是原型模式:
    原型模式无非就是克隆一个对象,其最简单的形式就是一个 clone() 函数,接受一个对象作为输入参数,返回输入对象的一个副本。在 Python 中可以使用 copy.deepcopy() 函数来完成。

  • 什么是副本:
    一个对象在 某一时间点完全 复制,时间是一个重要元素,因为它会影响克隆所包含的内容。

  • 引用和副本间的区别:
    如果A和B都持有同一个对象的引用,那么A修改对象后,B就能看到对象的修改,反之亦然。
    如果A和B都持有一个对象的副本,呢么A修改所持有的副本,B是看不到修改的,反之亦然。因为A和B所持有的副本是两个独立的内存地址。

####一、身边的例子

  • 细胞的分裂。细胞核分裂产生两个新的细胞核,这两个细胞都具有原来细胞相同的染色体、DNA等。
  • VTK(可视化工具套件)。VTK是一个开源的跨平台的系统,用于三位计算图形和图片处理以及可视化。VTK利用原型模式来创建几何元素。
  • Python中很多应用也都使用了原型模式。

####二、什么情况下使用

  1. 当我们已有一个对象,并希望创建该对象的一个完整副本时;
  2. 在我们知道对象的某些本分会被改变,但有希望保持原有的对象不变时;
  3. 我们想复制一个复杂的对象时。

####三、应用案例
下面我们来看一个案例,利用原型模式展示一个图书的各个版本信息

import copy
from collections import OrderedDict


class Book:
    def __init__(self, name, authors, price, **rest):
        '''rest的例子有:出版商、长度、标签、出版日期'''
        self.name = name
        self.authors = authors
        self.price = price
        self.__dict__.update(rest)

    def __str__(self):
        mylist = []
        ordered = OrderedDict(sorted(self.__dict__.items()))
        for i in ordered.keys():
            mylist.append('{}:{}'.format(i, ordered[i]))
            if i == 'price':
                mylist.append('$')
            mylist.append('\n')
        return ''.join(mylist)


class Prototype:
    def __init__(self):
        self.objects = dict()

    def register(self, identifiter, obj):
        self.objects[identifiter] = obj

    def unregister(self, identifier):
        del self.objects[identifier]

    def clone(self, identifier, **attr):
        found = self.objects.get(identifier)
        if not found:
            raise ValueError('Incorrect object identifier:{}'.format(identifier))
        obj = copy.deepcopy(found)
        obj.__dict__.update(attr)
        return obj


def main():
    b1 = Book('The Cprogramming Language', ('Brian W.Kernighan', 'Dennis M.Ritchie'), price=118,
              publisher='Prentice Hall', length=228, publication_date='1978-02-22',
              tags=('C', 'programming', 'algorithma', 'algorihma', 'data structures'))

    prototype = Prototype()
    cid = 'k&r-first'
    prototype.register(cid, b1)
    b2 = prototype.clone(cid, name='The CProgramming Language(ANSI)', price=48.99, length=274,
                         publication_date='1988-04-01', edition=2)
    for i in (b1, b2):
        print(i)
    print('ID b1:{}!= ID b2:{}'.format(id(b1), id(b2)))


if __name__ == '__main__':
    main()


http://www.niftyadmin.cn/n/1562741.html

相关文章

jboss7.1+jdk环境搭建

1 概述1.1 概述本文详细介绍了在Linux平台安装部署系统的步骤,供运维人员参考。本文的所有范例,建立在以下平台之上:硬件:Intel x86_64平台,64位CPU操作系统:CentOS 6.4 x86_64 SMP 64位操作系统JDK&#x…

Python从入门到精通--课程目录

####Python基础 第一章 起步 1.环境搭建 1.1.Windows 搭建Python环境1.2.Ubuntu 搭建Python环境1.3.Mac 搭建Python环境1.4.小结 2.我的第一个Python项目 2.1.新建项目2.2.运行项目2.3.发生了什么2.4.小结 第二章 入门 1.变量、字符串与数字 1.1.变量1.2.字符串1.3.数字1.4.小…

sublime在浏览器中访问

2019独角兽企业重金招聘Python工程师标准>>> 这里插入一下安装"view in browser"官方版的说明:(前提是得先安装package control插件) 1、通过"ctrlshiftp"打开命令面板 2、输入"install package"打…

近期文章与教程和其他情况说明

#####一&#xff0c;近期文章与教程预告 << 十七天十七个设计模式 >>将继续发布&#xff0c;我会尽快将此系列教程完成;<< Python从入门到精通 >>&#xff0c;我会在7月21日开始编写并发布;近期我也会发布一些小的知识点&#xff0c;比如** 装饰器* &…

MySQL双主如何解决主键冲突问题

搭建了个双主&#xff0c;突然想到如果表设置了自增主键的话&#xff0c;当业务同时向双库中插入一条数据&#xff0c;这时候情况是什么样子的呢&#xff1f; 比如&#xff1a;主库A和主库B上的一个表数据为&#xff1a; 12 ninhao 。当业务同时写入数据后主库A的数据是13 new…

第一章--第一节:环境搭建

负一、阅读前注意 本教程使用的Python版本是3.6.5&#xff0c;读者使用的Python版本尽量与本教程一致&#xff0c;最低版本必须是***Python3.5***版本本教程的开发环境是windows 10&#xff0c;其他操作系统亦可本教程的开发IDE是Atom&#xff0c;其他IDE亦可 零、Windows 搭…

Ubuntu16升级Python3

网上好多Ubuntu16.04升级Python的方法&#xff0c;但是大多教程都是使用源码安装的方式。这篇博文将会使用另一种方法将系统自带的Python3.5升级到Python3.6。 用过Ubuntu16.04的人都知道&#xff0c;这个版本Ubuntu的软件源安装列表中是没有Python3.6的安装包的&#xff0c;所…

mysql主从监控

1、mysql主从监控的主要思路Mysql主从的监控&#xff0c;其主要是监控从库上的一些重要参数&#xff1a;Slave_IO_Running: YesSlave_SQL_Running: YesMaster_Log_File: bin-log.003Relay_Master_Log_File: bin-log.003Read_Master_Log_Pos: 4Exec_master_log_pos: 4Seconds_Be…