封装 - 当 setter 已经公开时,为什么我们需要它?

2022-09-01 10:10:18

封装是隐藏数据。我想在这里听到一些非常有趣的答案。

当我们已经为变量声明 setter 方法时,保留变量的意义是什么?privatepublic

我理解封装的用法,但是当我们将 setter 作为公共时,保持变量的意义是什么,我们可以直接使用访问修饰符。privatepublic

是因为我们不想让其他人知道我们在后端存储数据或管理数据的确切方式吗?


答案 1

是因为我们不想让其他人知道我们在后端存储数据或管理数据的确切方式吗?

是的,这就是重点。它也与抽象和信息隐藏的概念有关。

您提供了一个公共 setter,当由类客户端调用该 setter 时,它将具有您已记录的效果。如何实际实现这种效果与客户无关。是否正在修改其中一个类属性?好的,让客户端知道,但不是你实际上正在修改变量的事实。将来,您可能希望修改类,以便它使用完全不同的东西(属性字典?外部服务?无论什么!并且客户端不会中断。

因此,您的 setter 是您提供给客户端的用于“修改此类属性”的抽象。同时,您正在隐藏您正在使用内部变量的事实,因为客户端不需要知道该事实。

(注意:这里我使用“属性”这个词作为通用概念,与任何具体的编程语言无关)


答案 2

我完全同意Konamiman的答案,但我想补充一点:

在某些情况下,你真的不想要这种抽象。这很好。

我喜欢在这里使用的一个简单示例是三维浮点向量的类:

class Vector3f {
public:
    float x;
    float y;
    float z;
};

你能把这些字段设为私有,并改为提供 setter 吗?当然可以。但在这里你可能会争辩说,这个类实际上应该提供一个浮点数元组,你不需要任何额外的功能。因此,添加 setter 只会使类复杂化,并且您宁愿将字段保留为公共字段。

现在,您可以轻松构建以后可能会咬到您的场景。例如,有一天你可能会得到一个要求,即不允许存储 s,如果有人试图这样做,应该抛出一个异常。但是,这样一个假设的未来问题应该不足以证明引入额外的抽象是合理的。Vector3fNaN

作为一名程序员,你需要决定哪些抽象对手头的问题有意义,哪些抽象只会妨碍你完成工作。不必要的抽象是过度工程化的,会损害你的生产力,就像不够抽象一样。

底线:不要因为有人声称这是好的做法而在任何地方盲目地使用设置器。相反,想想手头的问题,并考虑权衡利弊。