`
txf2004
  • 浏览: 6866097 次
  • 性别: Icon_minigender_1
  • 来自: 上海
社区版块
存档分类
最新评论

大话程序设计语言中的OOP机制

 
阅读更多

OOPObject-Oriented Programming(面向对象程序设计)就是选用面向对象的程序设计语言(Object-Oriented Programming LanguageOOPL),采用对象,类及其相关概念所进行的程序设计。

对面向对象的理解本身是无止境的,但是面向对象的程序设计语言却有一些可以摸索到的特征,下面就简单说说自己对面向对象语言特征的理解。

1、要有类的概念,定义的类可以被实例化。

面向对象之所以替代了一般的程序设计就是因为她将现实生活中的情况更加准确的用程序设计语言描述了出来。类的概念以及类实例化等等都是现实世界在程序设计语言中的具体表现。这样的好处是易维护,就像现实生活中那样,哪出错就去哪修改,最大程度的避免了“牵一发而动全身”的尴尬。

举个例子:人吃饭。这里如果按照非面向对象的思想来写,就是在一段代码中完完全全的写明白这个人如何去吃这个饭以及这个饭到底是什么样的饭等等,所有细节将都将在一个代码体中表现出来。而面向对象思想就不鼓励这样写,面向对象表现的更加接近实际。首先定义人这个类,然后为人加上各种方法(饿了之后的反应,大口吃,小口吃,饱了之后的反应等等)以及属性(饭量大小,喜好的饭菜等等)这样一来就将代码进行了解耦。这么做起来代码量增加了,但是为我们带来的好处是可观的。因为一旦需求改变非面向对象的设计就需要从头改起,从这个人开始从新描述这个整个的吃饭过程,一致描述到整个过程结束为止。而面向对象就不必这样,如果是人的变化则只需改动人这个类即可,其他类也是同一个道理。

2、继承和类层次结构

面向对象的另一个诱人的地方就是继承机制,父类有什么特征子类可以有选择的进行继承,子类不需要从零开始进行编写,从而达到提高编程效率的目的。

映射到现实生活中可能更加好理解。众所周知一切生物都是从简单生物一步一步进化而来,而且现在的各种生物依然在不断的进化当中(尽管很缓慢)。进化是什么,说白了就是把父辈的优良基因继承下来,然后自身还在不断地变异。这不就是面向对象中的继承么,父类的方法中有用的(优良的)继承下来,没有用的(劣质的)则淘汰(重写),自身还能有一些自己特有的(父类没有)的方法或者属性。用更加直白的话说就是:人从猴子进化而来,而不是大自然凭空造出来,这样的话大自然要做的仅仅就是在猴子的基础上稍微改造一下便产生了人,大自然是多么的明智啊!

3、对象、消息传递和方法

类有了,通过实例化类得到的对象也有了,那么下面要做的就是需要通过这些个对象来完成你要做的操作了。

我们所熟知的操作对象的方法就是“.”一个对象名然后在后面加一个“.”再后面就是跟这个对象的方法或者属性了。这就属于消息传递的方式,有些消息传递的过程中还需要一组参数,也就是我们所熟悉的方法需要的参数。对于一个类来说,它关于方法界面的定义规定了实例的消息传递协议,而它本身则决定了消息传递的合法范围。由于类是先于对象构造而成的,所以一个类为它实例提供了可以预知的交互方式。说白了就是在类中定义的方法通过实例化这个类就可以使用,但是必须严格遵从类中的定义罢了。也就是说虽然每个人都能吃饭但是具体到吃这个动作的时候你必须表明是谁(具体到对象)在吃饭,因为凭空说一个人吃饭一般情况下是没有意义。

4、对象自身引用

如果你对这个特点的文字描述不熟悉的话,那么你一定知道java或者C++中的this吧。

我们就来说说这个this到底是干嘛的。thisOOPLs中表明的是引用自身,这种机制使得在进行方法的设计和实现时并不需要考虑与对象联系的细节,而是从更高一级的抽象层次,也就是从类的角度来设计同类型的对象的行为特征。

还是举吃饭的例子,在人的吃这个方法中我们是这么写的:用手把饭放到嘴里。这里又涉及到两个属性,一个是手,一个是嘴。具体是谁的手,谁的嘴,总不能是我吃饭的时候把我手里的东西放到你的嘴里吧(那就不叫我吃饭了,那叫我喂你吃饭)。所以在定义人这个类的时候对于吃这个方法更好的办法是这么写:我的手把我手里的东西放到我的嘴里。而这里的“我”仅仅是一个代号,“我”可能是小李也可能是小王,这取决于实例化这个人的名字而定。所以在类中我们用this来表示本人,于是便有了this加“.”表示引用自身的方法或者属性。

5、重置(overriding

通过一种动态绑定机制的支持,是的子类在继承父类界面的前提下,用适合于自己的要求去置换父类中的相应的实现。

重置也叫重写,看汉字如果不熟悉,看英文(overriding)应该很熟悉吧。简单而言就是子类继承父类的方法,但是又觉得父类的方法有缺陷,进而重新定义了方法内容。映射到现实世界当中就是人类继承猴子(准确的说应该是灵长类)后自然就继承了“吃”这个方法,但是又重新定义了这个方法。灵长类一般是直接生吃,而人类则发明了很多种吃(煎炒烹炸等等),这属于重置(重写)。通过继承更加高效的进行编码,因为在猴子(或者说灵长类)这个类中可能仅仅“吃”这个方法不符合人们的要求,那么仅仅重置这一个方法就可以了,其他的原封不动即可。

6、类属类

类属是程序设计语言中普遍注重的一种参数多态机制,在OOPLs中也不例外。如果用过C++中的模板类或者C#中的泛型就会对这个概念感到熟悉。笔者所理解的类属就是通过参数的类型的不同来实现的一种多态机制。

还以人吃饭为例,饭可以定义为一个类,但是饭又包括馒头和米饭,对于不同的饭应该有不同的吃法所以说在吃这个方法中参数饭应该是类属类,根据类属类的具体情况来具体实现这个方法。也就是说在吃饭的时候首先应该判断是米饭还是馒头然后在进行吃的具体操作(用手还是用筷子)。

7、无实例的类

所谓无实例的类就是我们在C++java中常说的抽象类。那么抽象类的作用是什么?

抽象类,抽象方法这些都是我们经常提到也是用到的,实际想一下为什么要用到抽象类和抽象方法,尤其是抽象方法,仅仅一个方法的空壳而已。笔者认为这样做的好处是封装和多态。

还拿人吃饭来说,如果把人定义成一个普通的类,那么动物可以定义为一个抽象类,在动物这个抽象类中有吃这个抽象的方法。这样的话在人这个类继承动物这个抽象类的时候就自然而然的具有了吃这个方法(封装)但是人的吃和其他动物的吃又不同所以人的吃这个方法将在人这个类中具体的实现(多态)。这样看来抽象类就是类的更高层次的抽象,充分的体现了面向对象的封装,多态的特点。说到底还是为了高效的编码,最大限度的减少代码的重复性。

以上七个特点是OOPL的中的OOP机制,从这七个特点来看这些都是围绕面向对象中封装、继承、多态思想的具体体现而已。

对于面向对象我们犹如一个长不大的孩童——I have a long way to go.



回到目录下一篇

分享到:
评论

相关推荐

Global site tag (gtag.js) - Google Analytics