在面向对象编程中拥有类/结构的私有(private)/ protected 成员的目的是什么?让所有成员都公开有什么害处?
最佳答案
封装。 IE。隐藏类数据的实现。这允许您稍后更改它,而不会破坏所有客户端代码。例如。如果你有
class MyClass {
public int foo;
}
您的客户可能会编写如下代码
MyClass bar = new MyClass();
bar.foo++;
现在如果你意识到
foo
实际上应该是double而不是int,你改变它:class MyClass {
public double foo;
}
并且客户端代码无法编译:-(
使用设计良好的接口(interface),内部(私有(private)部分)的更改甚至可能包括将成员变量转换为计算,反之亦然:
class Person {
public String getName();
public String getStreetAddress();
public String getZipCode();
public String getCountryCode();
public int hashCode();
}
(为了简单起见,使用 String 属性——在现实世界的设计中,其中一些可能应该有自己的类型。)
使用这种设计,您可以自由地进行例如介绍
Address
内部属性,其中将包含街道地址、邮政编码和国家/地区代码,并重写您的访问器以使用此私有(private)成员的字段,而您的客户不会注意到任何事情。您还可以自由决定是每次都计算哈希码,还是将其缓存到私有(private)变量中以提高性能。但是,如果该缓存字段是公开的,那么任何人都可以更改它,这可能会破坏哈希映射行为并引入细微的错误。所以封装是保证对象内部状态一致性的关键。例如。在上面的示例中,您的设置者可以轻松验证邮政编码和国家/地区代码,以防止设置无效值。您甚至可以确保邮政编码格式对实际国家/地区有效,即确保跨多个属性的有效性标准。使用精心设计的界面,您可以通过例如强制执行此绑定(bind)。仅提供一个 setter 来同时设置两个属性:
public void setCountryCodeAndZip(String countryCode, String zipCode);
但是,对于公共(public)字段,您根本没有这些选择。
私有(private)字段的一个特殊用例是不可变对象(immutable对象)。这在例如Java,示例为
String
和 BigDecimal
.这些类根本没有公共(public) setter ,这保证了它们的对象一旦创建就不会改变它们的状态。这可以实现许多性能优化,并使它们更易于在例如多线程程序,ORM 等。
关于language-agnostic - 类中私有(private)成员的目的,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2374988/