設計模式——代理模式(C++)

/*****************************************
Copyright (c) 2016 Jingshuang Hu

@filename:Subject.h
@datetime:2016.09.19
@author:HJS
@e-mail:[email protected]
@blog:http://blog.csdn.net/hujingshuang
*****************************************/
#ifndef _SUBJECT_H
#define _SUBJECT_H

#include <string>

// 定義接口
class Subject {
public:
    virtual void request() = 0;             // 請求
    virtual void open() = 0;                // 打開
    virtual void close() = 0;               // 關閉
};

// 真正做事的對象,受代理(Proxy)的控制和訪問
class concreteSubject : public Subject {
private:
    std::string name;
public:
    concreteSubject(std::string name);
    virtual void request();
    virtual void open();
    virtual void close();
};

// 代理
class Proxy : public Subject {
private:
    Subject* subject;
public:
    Proxy();
    Proxy(Subject* subject);
    void attach(Subject* subject);          // 添加(設置)
    virtual void request();
    virtual void open();
    virtual void close();
};

#endif // _SUBJECT_H
/*****************************************
Copyright (c) 2016 Jingshuang Hu

@filename:Subject.cpp
@datetime:2016.09.19
@author:HJS
@e-mail:[email protected]
@blog:http://blog.csdn.net/hujingshuang
*****************************************/
#include "Subject.h"
#include <iostream>

using namespace std;

// 抽象接口
void Subject::request() {}

void Subject::open() {}

void Subject::close() {}

// 具體
concreteSubject::concreteSubject(string name) {
    this->name = name;
}

void concreteSubject::request() {
    cout << name + " requesting..." << endl;
}

void concreteSubject::open() {
    cout << name + " is open." << endl;
}

void concreteSubject::close() {
    cout << name + " is close" << endl;
}

// 代理
Proxy::Proxy() {}

Proxy::Proxy(Subject* subject) {
    this->subject = subject;
}

// 當然,如果你喜歡的話,這裏可以做一個表來記錄這些被代理的對象(我這裏就直接覆蓋了。。)
void Proxy::attach(Subject* subject) {
    this->subject = subject;
}

// 代理收到客戶端的請求,然後轉發給被代理的對象
void Proxy::request() {
    subject->request();
}

void Proxy::open() {
    subject->open();
}

void Proxy::close() {
    subject->close();
}
/*****************************************
Copyright (c) 2016 Jingshuang Hu

@filename:main.cpp
@datetime:2016.09.19
@author:HJS
@e-mail:[email protected]
@blog:http://blog.csdn.net/hujingshuang
*****************************************/
#include <iostream>
#include "Subject.h"

using namespace std;

// 代理模式
// 比如有兩個對象,它們具有請求、打開、關閉的功能,而作爲程序員,並不想對每個對象分別進行操作
// 或者是想對對象添加某些修飾方法,因此採用代理模式將原來的【方法一】改成【方法二】

int main() {
    concreteSubject* subjectA = new concreteSubject("A");
    concreteSubject* subjectB = new concreteSubject("B");

    // 【方法一】對每一個對象,都調用自己對應的方法來達到目的。
    //subjectA->request();
    //subjectA->open();
    //subjectA->close();

    //subjectB->request();
    //subjectB->open();
    //subjectB->close();

    // 【方法二】爲對象添加代理,此後將由代理進行操作,而不直接操作該對象。
    Proxy* proxy = new Proxy();

    proxy->attach(subjectA);
    proxy->request();
    proxy->open();
    proxy->close();

    // 交給代理
    proxy->attach(subjectB);
    proxy->request();
    proxy->open();
    proxy->close();

    system("pause");
    return 0;
}
// 注意:代理模式與裝飾者模式的區別
// 代理模式:爲對象提供一個虛擬的替身,並且可以爲其添加修飾方法。可以保護真實對象不受到不必要的訪問,其意圖與裝飾模式區別很大!
// 裝飾模式:爲對象提供包裝,裝飾對象。而其主要目的就是:將對象經過層層包裝,使其方法更加豐富,甚至是改變對象的行爲。

發佈了117 篇原創文章 · 獲贊 391 · 訪問量 62萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章