使用getter和setter(只获取和设置)而不是简单地为这些变量使用公共字段有什么好处?

如果getter和setter所做的不仅仅是简单的get/set,我可以很快地解决这个问题,但我不是100%清楚如何做到:

public String foo;

比:

private String foo;
public void setFoo(String foo) { this.foo = foo; }
public String getFoo() { return foo; }

而前者需要的样板代码要少得多。


当前回答

来自数据隐藏的获取者和设置者。数据隐藏意味着我们正在向外部人员或外部人员/事物隐藏无法访问的数据这是OOP中一个有用的特性。

例如:

如果您创建了一个公共变量,您可以访问该变量并在任何地方(任何类)更改值。但如果创建为私有,则该变量无法在除声明的类之外的任何类中查看/访问。

public和private是访问修饰符。

那么我们如何在外部访问该变量:

这是获得者和获得者的地方。您可以将变量声明为private,然后可以为该变量实现getter和setter。

示例(Java):

private String name;

public String getName(){
   return this.name;
}

public void setName(String name){
   this.name= name;
}

优势:

当任何人想要访问或更改/设置平衡变量的值时,他/她必须获得许可。

//assume we have person1 object
//to give permission to check balance
person1.getName()

//to give permission to set balance
person1.setName()

您也可以在构造函数中设置值,但稍后需要时要更新/更改值,必须实现setter方法。

其他回答

代码不断演变。private非常适合需要数据成员保护的情况。最终,所有的类都应该是一种“小程序”,它有一个定义良好的接口,你不能只使用它的内部结构。

也就是说,软件开发并不是要设置课程的最终版本,就好像你在第一次尝试时按下了一些铸铁雕像一样。当你使用它时,代码更像粘土。它随着你的发展而发展,并进一步了解你正在解决的问题领域。在开发过程中,类之间可能会发生不应有的交互(您计划排除的依赖关系)、合并或拆分。因此,我认为争论归结为人们不想虔诚地写作

int getVar() const { return var ; }

所以你有:

doSomething( obj->getVar() ) ;

而不是

doSomething( obj->var ) ;

getVar()不仅在视觉上很嘈杂,而且给人一种错觉,认为getingVar(()在某种程度上是一个比实际更复杂的过程。如果你的类有一个passthrough setter,那么你(作为类编写者)如何看待var的神圣性对你的类的用户来说尤其令人困惑——那么你似乎在设置这些门来“保护”你坚持认为有价值的东西,(var的神圣性)但即使你承认,任何人只要进来并将var设置为他们想要的任何值,而你甚至不去偷看他们在做什么,那么var的保护就没有多大价值。

所以我按如下方式编程(假设采用“敏捷”类型的方法——即当我编写代码时不知道它将要做什么/没有时间或经验来规划一个复杂的瀑布式界面集):

1) 从具有数据和行为的基本对象的所有公共成员开始。这就是为什么在我所有的C++“示例”代码中,你会注意到我到处使用结构而不是类。

2) 当对象对数据成员的内部行为变得足够复杂时(例如,它喜欢以某种顺序保存内部std::list),就会编写访问器类型函数。因为我是自己编程的,所以我并不总是立即将成员设置为私有,但是在类的进化过程中,成员将被“提升”为受保护或私有。

3) 完全充实并对其内部有严格规则的类(即,它们确切地知道自己在做什么,你不能“操”(技术术语)它的内部)被赋予类名称,默认为私有成员,只有少数成员被允许公开。

我发现这种方法可以让我避免在一个类进化的早期阶段,当大量数据成员被迁移、转移等时,坐在那里虔诚地编写getter/setter。

因为从现在起2周(月、年),当您意识到setter需要做的不仅仅是设置值时,您还将意识到该属性已直接用于238个其他类:-)

我花了很长时间来思考Java案例,我相信真正的原因是:

接口的代码,而不是实现接口只指定方法,不指定字段

换句话说,在接口中指定字段的唯一方法是提供一个用于写入新值的方法和一个用于读取当前值的方法。

这些方法是臭名昭著的getter和setter。。。。

从面向对象设计的角度来看,这两种选择都会削弱类的封装,从而对代码的维护造成损害。对于讨论,您可以查看这篇优秀的文章:http://typicalprogrammer.com/?p=23

访问器和赋值器的一个优点是可以执行验证。

例如,如果foo是公共的,我可以很容易地将其设置为null,然后其他人可以尝试调用对象上的方法。但它已经不在了!使用setFoo方法,我可以确保foo从未设置为null。

访问器和赋值器也允许封装-如果你不应该在值设置后看到它(也许它在构造函数中设置,然后被方法使用,但不应该被更改),那么任何人都不会看到它。但如果您允许其他类查看或更改它,则可以提供适当的访问器和/或赋值器。