美文网首页Java知识
面向对象(上)

面向对象(上)

作者: 不小心丢了 | 来源:发表于2019-08-01 15:21 被阅读0次

    面向对象与面向过程

    现实生活中存在着各种形态不同的事物,这些事物之间存在着各种各样的联系。
    在程序中使用对象来映射现实中的事物,使用对象的关系来描述事物间的联系,这种思想就是面向对象。

    面向过程就是分析出解决问题所需要的步骤,然后用函数把这些步骤一一实现,使用的时候依次调用就可以了。

    面向对象则是把构成问题的事务按照一定规则划分为多个独立的对象,然后通过调用对象的方法来解决问题。

    面向对象的特点

    1)封装性

    封装是面向对象的核心,将对象的属性和行为封装起来,不需要让外界知道具体实现细节,这就是封装思想
    例如,用户使用计算机,只需要使用手指敲键盘就可以了,无需知道计算机内部是如何工作的,即使用户可能碰巧知道计算机的原理,但在使用时并不完全依赖计算机工作原理这些细节。

    2)继承性

    继承性描述的是类与类之间的关系,通过继承,可以在无需重新编写原有类的情况下,对原有类的功能进行扩展。

    3)多态性

    多态性指的是在程序中允许出现重名现象,它指在一个类中定义的属性和方法被其他类继承后,它们可以具有不同的数据类型和表现出不同的行为,这使得同一个属性和方法在不同的类中具有不同的语义。
    例如听到“Cut”这个单词时,理发师的行为是剪发,演员的行为表现是停止表演,不同的对象所表现的行为是不一样的。

    类与对象

    面向对象的编程思想,力图让程序中对事物的描述与该事物在现实中的形态保持一致。为了做到这一点,面向对象的思想中提出了两个概念,即类和对象。其中,类是对某一类事物的抽象描述,而对象用于表示现实中该类事物的个体。

    类的定义

    在面向对象的思想中,最核心的就是对象。为了在程序中创建对象,首先需要定义一个类。类是对象的抽象,它用于描述一组对象的共同特征和行为。类中可以定义成员变量和成员方法,其中成员变量用于描述对象的特征,也被称为属性;成员方法用于描述对象的行为,可简称为方法。

    class Person {

    int age;//定义int类型的变量age

    //定义speak()方法

    void speak(){

    System.out.println("大家好。我今年"+age+"岁");

    }

    }

    其中Person是类名,age是成员变量,speak()是成员方法。在成员方法speak()中可以直接访问成员变量age。

    在Java中,定义在类中的变量被称为成员变量定义在方法中的变量被称为局部变量,如果在某个方法中定义的局部变量与成员变量同名,这种情况是允许的,此时方法中通过变量名访问到的是局部变量,而并非成员变量。

    对象的创建与使用(new)

    在Java中可以通过new关键字来创建对象,具体格式如下:

    类名  对象名称 = new  类名 () ;

    例如创建Person类的实例对象代码如下:

    Person  p = new  Person () ;

    在上面的代码中,“new Person()”用于创建Person类的一个实例对象,“Person p” 则是声明了一个这样Person类型的变量p。中间的等号用于将Person对象在内存中的地址赋值给变量p,这样变量p便持有了对象的引用。

    内存分析

    在创建Person对象后,可以通过对象的引用来访问对象所有的成员,具体格式如下

    对象引用.对象成员

    运行结果

    p1、p2分别引用了Person类的两个实例对象,从运行结果可以看出,p1、p2在调用speak()方法时,打印的age值不同。这是因为p1对象和p2对象是两个完全独立的个体,它们分别拥有各自的age属性,对p1对象的age属性进行赋值并不会影响到p2对象age属性的值、程序运行期间,p1、p2引用的对象在内存中的状态如下图所示

    p1.p2对象在内存中的状态

    在上面的代码中,通过"p1.age=18"将p1对象属性赋值为18,但并没有对p2对象的age属性进行赋值,按理说p2对象的age属性应该是没有值的。但从运行结果看出,p2对象的age属性值为0,。这是因为在实例化对象时,Java虚拟机会自动为为成员变量进行初始化,针对不同类型的成员变量,Java虚拟机会赋予不同的初始值。

    成员变量初始化值

    当对象被实例化后,在程序中可以通过对象的引用变量来访问该对象的成员。需要注意的是,当对象没有任何变量引用这个对象是,它将成为垃圾对象,不能再被使用。

    运行结果

    创建了一个Person类的实例对象,并两次强调了该对象的say()方法。第一次调用say()方法时可以正常打印,但在将变量p1的值为null,时,再次调用say()方法时抛出了空指针异常。在Java中,null是一种特殊的变量,当一个变量的值为null时,则表示该变量不指向任何一个对象。在程序运行时,当把p1变量置为null,那么被p1所引用的Person对象就会失去引用,成为垃圾对象。

    类的封装(private关键字)

    在设计一个类时,应该对成员变量的访问做一些限定,不允许外界随意访问,这就需要实现类的封装
    所谓类的封装是指在定义一个类时,将类中的属性私有化,即使用private关键字来修饰
    私有属性只能在它所在类中被访问,如果外界想要访问私有属性,需要提供一些使用public修饰的公有方法,其中包括获取属性值的getXxx方法和设置属性值的setXxx方法。

    运行结果

    使用private关键字将属性name和age声明为私有,对外界提供了几个公有方法。其中,getName()方法用于获取属性的值,setName()用于设置name的值,同理,getAge()和setAge()方法用于获取和设置age属性的值。在main()方法中创建了Student对象,并调用setAge()方法传入一个负数-30,在setAge()方法中会对参数stuAge的值进行检查,由于当前传入的参数的值小于0,因此会输出“对不起,您输入的年龄不合法…”信息,age属性没有被赋值,仍为初始值0。

    构造方法

    从前面的知识可以发现,实例化一个类的对象后,如果要为这个对象中的属性赋值,则必需要通过直接访问对象的属性或调用setXxx方法的方式才可以。如果需要在实例化对象的同时就为这个这个对象的属性进行赋值,可以通过构造方法来实现。构造方法是类的一个特殊成员,它会在类实例化对象时被自动调用。

    构造方法的定义

    在一个类中定义的方法,如果同时满足下面三个条件,该方法称为构造方法,具体如下。

    ①方法名与类名相同。
    ②在方法名的前面没有返回值类型的声明(构造方法前面加void就变成了成员方法)
    ③在方法中不能使用return语句返回一个值,但是可以单独写return语句来作为方法的结束。

    构造方法Person 运行结果

    new Person()语句的作用除了会实例化Person对象,还会调用构造方法Person()。

    在一个类中除了定义无参的构造方法,还可以定义有参的构造方法,通过有参的构造方法就可以实现对属性的赋值。

    有参构造方法 运行结果

    构造方法的重载

    与普通方法一样,构造方法也可以重载,在一个类中可以定义多个构造方法,只要每个构造方法的参数类型或参数个数不同即可。
    在创建不同对象时,根据传入参数的不同,分别调用不同的构造方法。

    在Java中的每一个类都至少有一个构造方法,如果在一个类中没有定义构造方法,系统会自动为这个类创建一个默认的构造方法,这个默认的构造方法没有任何参数,在其方法体中没有任何代码,即什么也不做。下面程序中的Person类的两种写法效果完全一样:

    第一种写法

    class Person{
    }

    第二种写法

    class Person{
        public  Person(){
    }
    }

    对于第一种写法,类中虽然没有声明构造方法,但仍可以使用new Person()来创建Person类的实例对象。由于系统提供的构造方法往往不能满足需求,因此可以自己在类中定义构造方法,一旦为该类定义了构造方法,系统就不再提供默认的构造方法了。所以建议在一个类中如果自己定义了一个有参构造方法,最好再定义一个无参的构造方法。

    相关文章

      网友评论

        本文标题:面向对象(上)

        本文链接:https://www.haomeiwen.com/subject/jnfirctx.html