干净的C ++粒度的朋友等同? (答案:律师 - 客户成语) [英] clean C++ granular friend equivalent? (Answer: Attorney-Client Idiom)

查看:103
本文介绍了干净的C ++粒度的朋友等同? (答案:律师 - 客户成语)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

为什么C ++有 public 任何人都可以调用的成员和 friend 声明公开 all private 成员提供给 外部类或方法,但不提供任何语法向特定成员公开给定的呼叫者?



我想表达一些例程的接口,只由已知的调用者调用,而不必给这些调用者完全访问所有privates,这感觉像一个合理的东西想要的。最好的我可以想出自己(下面),其他人的建议迄今为止围绕习语/不同间接性的模式,其中我真的只是想要一种方式有单个,简单的类定义明确指示什么呼叫者(比我我的孩子绝对任何人)可以访问哪些成员。

  //我可以授予Y :: usesX(...)选择性X :: restricted(...)访问更干净? 
void Y :: usesX(int n,X * x,int m){
X :: AttorneyY :: restricted(* x,n)
}

struct X {
class AttorneyY; //代理限制部分或全部Y的状态。
private:
void restricted(int); //最好选择性地使用。
friend class AttorneyY; //给予可信的成员类私有访问。
int personal_; //真正的私人状态...
};

//单一抽象权限。可以添加更多的朋友或转发。
class X :: AttorneyY {
friend void Y :: usesX(int,X *,int);
inline static void restricted(X& x,int n){x.restricted(n); }
};

我离软件组织大师不远,但感觉界面简单,最小特权在语言的这个方面是直接矛盾的。我的愿望的更清楚的例子可能是 Person 类与 takePill(Medicine *) tellTheTruth() forfeitDollars(unsigned int)只有 Physician Judge TaxMan 实例/成员方法分别应考虑调用。



答案:对于每个主要接口方面,我需要一次性的代理或接口类。从德鲁大厅接受博士Dobbs - 友谊和律师 - 客户成语



上面的代码最初称为包装器类'Proxy',而不是'Attorney'指针而不是引用,但在其他方面等同于Drew发现的东西,然后我认为这是最好的普遍知道的解决方案。 (不要拍我自己在后面太难了...)我也改变了'restricted'的签名以演示参数转发。这个成语的总成本是每个权限集的一个类和一个朋友声明,每个批准的调用者的一个朋友声明,以及每个权限集的每个公开方法一个转发包装器。下面大多数更好的讨论围绕着转发调用样板,一个非常类似的Key习语避免了较少的直接保护。

解决方案

律师 - 客户成语可能是您要查找的内容。机制与您的成员代理类解决方案没有太大的区别,但是这种方式更加惯用。


Why does C++ have public members that anyone can call and friend declarations that expose all private members to given foreign classes or methods but offer no syntax to expose particular members to given callers?

I want to express interfaces with some routines to be invoked only by known callers without having to give those callers complete access to all privates, which feels like a reasonable thing to want. The best I could come up with myself (below) and suggestions by others so far revolve around idioms/pattern of varying indirectness, where I really just want a way to have single, simple class definitions that explicitly indicate what callers (more granularly than me, my children, or absolutely anybody) can access which members. What is the best way to express the concept below?

// Can I grant Y::usesX(...) selective X::restricted(...) access more cleanly?
void Y::usesX(int n, X *x, int m) {
  X::AttorneyY::restricted(*x, n);
}

struct X {
  class AttorneyY;          // Proxies restricted state to part or all of Y.
private:
  void restricted(int);     // Something preferably selectively available.
  friend class AttorneyY;   // Give trusted member class private access.
  int personal_;            // Truly private state ...
};

// Single abstract permission.  Can add more friends or forwards.
class X::AttorneyY {
  friend void Y::usesX(int, X *, int);
  inline static void restricted(X &x, int n) { x.restricted(n); }
};

I'm nowhere near being a software organization guru, but it feels like interface simplicity and the principle of least privilege are directly at odds in this aspect of the language. A clearer example for my desire might be a Person class with declared methods like takePill(Medicine *) tellTheTruth() and forfeitDollars(unsigned int) that only Physician, Judge, or TaxMan instances/member methods, respectively, should even consider invoking. Needing one-time proxy or interface classes for each major interface aspect sits ill with me, but please speak up if you know I'm missing something.

Answer accepted from Drew Hall: Dr Dobbs - Friendship and the Attorney-Client Idiom

The code above originally called the wrapper class 'Proxy' instead of 'Attorney' and used pointers instead of references but was otherwise equivalent to what Drew found, which I then deemed the best generally known solution. (Not to pat myself on the back too hard...) I also changed the signature of 'restricted' to demonstrate parameter forwarding. The overall cost of this idiom is one class and one friend declaration per permission set, one friend declaration per set approved caller, and one forwarding wrapper per exposed method per permission set. Most of the better discussion below revolves around the forwarding call boilerplate that a very similar 'Key' idiom avoids at the expense of less direct protection.

解决方案

The Attorney-Client idiom may be what you're looking for. The mechanics are not too different from your member proxy class solution, but this way is more idiomatic.

这篇关于干净的C ++粒度的朋友等同? (答案:律师 - 客户成语)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆