Exceptional C++

【Exceptional C++(12)】Classes之间的关

2018-01-29  本文已影响10人  downdemo

问题

class GenericTableAlgorithm {
public:
    GenericTableAlgorithm(const string& table);
    virtual ~GenericTableAlgorithm();
    // process()成功时返回true,该函数负责所有工作
    // 读取表格中的记录,为每笔记录调用Filter决定是否置于待处理的rows中
    // 当待处理的rows组成的list架构完成,为每个row调用ProcessRow()
    bool process();
private:
    virtual bool Filter(const Record&);
    virtual bool ProcessRow(const PrimaryKey&) = 0;
    class GenericTableAlgorithmImpl* pimpl_;
};
class MyAlgorithm : public GenericTableAlgorithm {
// 重写Filter和ProcessRow做出特定行为
};
int main()
{
    MyAlgorithm a("Customer");
    a.Process();
}

解答

// File gta.h
// 提供一个公开接口封装共用功能使之成为一个template method
// 可巧妙地被隔离,使本身成为一个集中注意力的class
// 客户目标锁定GenericTableAlgorithm的外部使用者
class GTAClient;
class GenericTableAlgorithm {
public:
    // 构造函数现在接受一个具象的implementation对象
    GenericTableAlgorithm(const string& table, GTAClient& worker)
    // 现在从继承关系抽离出来了,不需要用虚析构函数
    ~GenericTableAlgorithm();
    bool Process();
private:
    class GenericTableAlgorithmImpl* pimpl_;
};
// File gtaclient.h
// 提供一个抽象接口,目的是提供扩展性
// 这是GenericTableAlgorithm的一个实作细节,与外部client无关
// 可被巧妙抽离为一个注意力集中的抽象protocal类
// 客户目标锁定concrete "implementation detail" classes的撰写者
// 他们使用并扩展GenericTableAlgorithm
class GTAClient {
public:
    virtual ~GTAClient() = 0;
    virtual bool Fliter(const Record&);
    virtual bool ProcessRow(const PrimaryKey&) = 0;
};
// File gtaclient.cpp
bool GTAClient::Fliter(const Record&)
{
    return true;
}
class MyWorker : public GTAClient {
// 重写Filter和ProcessRow做出特定行为
};
int main()
{
    GenericTableAlgorithm a("Customer", MyWorker());
    a.Process();
}
上一篇 下一篇

猜你喜欢

热点阅读