【发布时间】:2014-08-04 16:19:09
【问题描述】:
这是一个架构问题。程序员经常遇到这种封装问题,但我还没有看到一个完整干净的解决方案。
相关问题:
readonly class design when a non-readonly class is already in place
Controlling read/write access to fields
通常,在 OOP 范式中,对象将其数据存储在字段中。类自己的方法可以完全访问其字段。当需要返回值时,只返回一份数据,这样外部代码就无法破坏数据。
现在假设数据片段很复杂,因此它们本身封装在类对象中,并且这些对象不能轻易复制。现在,如果您从某个属性返回此类对象,则外部代码与您的内部代码具有相同的访问权限。例如,如果您返回一个List<int>,每个人都可以向它添加值。这通常是不可取的。
通常使用只读包装器解决此问题 - 在返回之前将完全访问的内部对象包装在只读包装器中。这种方法的问题在于包装器可能无法很好地替代被包装的值——包装器是一个不同的类。 (如果您从可修改类派生只读包装器(或反之亦然),那么任何人都可以将“只读”对象向上转换/向下转换为可修改对象,从而破坏保护。)
我想要这样的模式:
- 数据(例如,
int值)具有“公共/只读 API”和“私有/可修改 API”。 - 只有对象创建者才能访问“私有/可修改 API”。
- 私有/公共 API 可能同时具有被动部分(例如方法、属性)和主动部分(例如事件)。
- 除非在对象创建阶段,否则不应使用委托。所有电话都应该是直接的。
- 从“公共/只读 API”(最好也从“私有/可修改 API”)访问内部数据应尽可能直接。在编写此类对象时,我不希望堆积一大堆包装器。
以下是示例界面:
interface IPublicApi {
int GetValue();
}
interface IPrivateApi {
void SetValue(int value);
}
interface IPrivateConsumer {
void OnValueChanged(); //Callback
}
我设计了这样的方案。我希望你批评我的解决方案或给出你自己的解决方案。
【问题讨论】:
标签: c# oop architecture encapsulation