c++ - 更多类的模板化律师-客户习语

标签 c++ templates design-patterns idioms

我试图将 Attorney-Client Idiom(称为 PassKey Idiom)和这个应用于两个类(class)。

我解释一下:

我有一个名为 Secret 的类,其中包含 nameage 作为私有(private)成员。我创建了一个 Attorney 类,它为 Secret 类中的每个成员定义了 2 个 getter。

我想创建 2 个类:

  1. showAge 只能访问 1 个 getter
  2. showAgeAndName 可以访问两个 getter。

到目前为止一切正常,但查看代码,它不是很好维护:如果我将新成员添加到我的 Secret 并想要对新的 getter 进行特定访问,我必须添加另一个类并且以大量复制粘贴结束。

那么有没有更好的选择,比如:使用工厂设计模式/增强模板类......

下面是我的代码:

#include <string>
#include <iostream>

using namespace std;

class Secret;
class showAge;
class showAgeAndName;

template<typename T>
class Attorney
{
private:
    friend T;
    Attorney(const Attorney&) {}
    Attorney() {}   
};

class Secret
{
public:
    std::string getAge(Attorney<showAge>) noexcept { return "Age is " + to_string((long long)age); }
    std::string getName(Attorney<showAgeAndName>) noexcept { return "Name is " + name; }
private:
    int age{36};
    std::string name{"Mike"};
};

class showAge
{
public:
    showAge() noexcept {};

    void showInfos(Secret& src)
    {
        std::cout << src.getAge(Attorney<showAge>()) << std::endl;
    }
};

class showAgeAndName
{
public:
    showAgeAndName() noexcept {};

    void showInfos(Secret& src)
    {
        std::cout << src.getName(Attorney<showAgeAndName>()) << std::endl;
    }
};

int main() {
    Secret s;
    showAge prA;    
    showAgeAndName prAn;
    prA.showInfos(s);
    prAn.showInfos(s);
}

谢谢

最佳答案

在我看来,这种模式带来的麻烦多于它的值(value)。

相反,您可能会考虑为每个访问角色定义接口(interface),然后通过对适当接口(interface)类型的引用来传递对象。这可能更具可读性和直观性,尽管它仍然需要您为每个角色定义和维护接口(interface)。

应该选择接口(interface)和它们公开的成员函数以适应访问角色。您不一定需要为每个功能提供单独的界面。如果你认为你这样做,我会将其视为 code smell并以此为线索重新评估设计。在使用律师-客户/密码模式时也是如此。

Attorney-Client/PassKey 模式的唯一优点是它不需要成员函数是虚拟的。但是很有可能是虚函数的性能开销is not important to your application .

缺点是 Attorney-Client/PassKey 模式鼓励您根据特定用户设计“接口(interface)”(如在访问 Secret 的特定类中)。这将创建 coupling .最好根据可以适当分配的通用角色来考虑。

关于c++ - 更多类的模板化律师-客户习语,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53172759/

相关文章:

c++ - 需要帮助修改 C++ 应用程序以在 Linux 中接受连续的管道输入

perl - 如何在 Perl 中格式化日期?

java - 指定扩展类的通用类型参数?

c++ - 使用 OpenGL 着色器在 C++ 中以 2D 形式绘制 4D 点

c++ - 如何取回长整数的两个分量

c++ - 有没有办法使用模板特化将 new 与 new [] 分开?

java - 好的做法 : API and MVC - where should I put method/function with SQL query for API

python - 工厂方法模式与多处理队列的使用冲突

c++ - 无法加载符号,即使它存在于 .so 文件中?

c++ - 使用另一个类模板专门化一个类模板时, `template<>` 是可选的吗?