Skip to content

面向对象

基本认识

对象

java
自然界中的任何事物,都可以通过分析其特征和行为将其描述的完整,理解为一个对象。

对象就是现实世界中客观存在的一个实体、一个个例、一个实例

属性

ts
一类事物共同拥有的信息,称之为特征,在程序中使用属性来描述。

方法

ts
一类事物共同拥有的动作,称之为行为,在程序中使用方法来描述。

类和对象

类和对象的关系:类是对象的抽象,对象是类的具体

ts
类是对象的抽象。类是一个抽象的概念,比如:人类,动物类,学生类等等……
对象是类的具体。对象是一个具体的概念,比如:赵四,家里的狗狗,小明同学等等……

学生类 class

ts
特征--属性:姓名、年龄、性别、身高、体重、爱好、联系方式、学号
属性也叫成员变量,也叫实例变量,也叫字段,英文名称:field 字段

行为--方法:学习  吃饭  睡觉
方法,也叫实例方法,注意,这里使用的方属于实例方法,也就是不能使用static修饰;英文名称:method 方法

静态方法和实例方法区别

ts
修饰关键字不同:
	静态方法有static关键字 实例方法没有

调用方式不同:
	静态方法直接书写方法名调用 
    实例方法必须先new对象;通过对象名加点调用
    
实例级别 也就是 对象级别

实例变量(属性)

ts
实例变量
  定义位置:直接定义在类中
  作用范围:整个类中都可以访问
  重名问题:可以与局部变量(方法中的变量)重名 局部变量优先使用 就近原则
  默认值:有默认值 与数组的默认值原则相同
  存储位置:因为实例属性保存在对象中,而对象存在堆中,全部存储在堆中
  生命周期:随着对象的创建而存在 随着对象被垃圾回收(GC)而死亡

存储位置:对象名存储在栈中,对象值存储在堆中,存在默认值,默认值的语法同数组相同。

image-20250224110957673

描述局部变量实例变量
定义位置方法或方法内的结构当中类的内部,方法的外部
默认值无默认值有默认值(与数组相同)
使用范围从定义行到包含其结构结束本类有效
命名冲突不允许重名可与局部变量重名,局部变量优先
存储位置基本数据类型存在栈中,引用数据类型名字在栈,值在堆因为实例属性保存在对象中,而对象存在堆中,全部存储在堆中
生命周期随着方法的入栈而生效,随着方法的出栈而死亡随着对象的创建而存在 随着对象被垃圾回收(GC)而死亡
java
package com.object;

public class Vtuber {
    // 实例变量 属性
    String name;
    int age;
    char sex;
    double weight;
    double height;
    String hobby;
    // 实例方法
    public void singing(){
        String name = "Aqua";
        System.out.println("海想列车 只在梦中见过一点点~~~");
    }
    public void gaming(){
        System.out.println("Apex start!!!");
    }
    public void myInfo(){
        int age = 5; // 可以跟实例变量一样,就近原则
        System.out.println("我的名字是 " + name);
        System.out.println("我的年龄是 " + age); // 5
        System.out.println("我的身高是 " + height);
        System.out.println("我的体重是 " + weight);
        System.out.println("我的性别是 " + sex);
        System.out.println("我的爱好是 " + hobby);
    }

    public static void main(String[] args) {
        // 创建一个 实例对象
        // 格式:类名 对象名 =  new 类名();
        Vtuber sakuna = new Vtuber();
        // 给实例属性赋值 使用对象名访问属性 给属性赋值
        // 格式:对象名.属性名 = 值;
        sakuna.name = "yuuki sakuna";
        sakuna.age = 10000;
        sakuna.sex = '女';
        sakuna.height = 148;
        sakuna.weight = 44.5;
        sakuna.hobby = "Sing and game";
        // 使用对象名访问方法 格式:对象名.方法名();
        sakuna.singing();
        sakuna.gaming();
        sakuna.myInfo();
    }
}
java

实例方法

ts
普通方法格式:访问修饰符 + 返回值类型 类名(){}

public 返回值类型 方法名 (){
    
}

特征--属性:姓名、年龄、性别、身高、体重、爱好、联系方式、学号 属性也叫成员变量,也叫实例变量,也叫字段,英文名称:field 字段

行为--方法:学习 吃饭 睡觉 方法,也叫实例方法,注意,这里使用的方属于实例方法,也就是不能使用static修饰;英文名称:method 方法

实例方法和静态方法对比

ts
修饰关键字不同:
	静态方法有static关键字 实例方法没有

调用方式不同:
	静态方法直接书写方法名调用 
    实例方法必须先new对象;通过对象名加点调用
    
实例级别 也就是 对象级别
java
package com.object;

public class Vtuber {
    // 实例变量 属性
    String name;
    int age;
    char sex;
    double weight;
    double height;
    String hobby;
    // 实例方法
    public void singing(){
        String name = "Aqua";
        System.out.println("海想列车 只在梦中见过一点点~~~");
    }
    public void gaming(){
        System.out.println("Apex start!!!");
    }
    public void myInfo(){
        int age = 5; // 可以跟实例变量一样,就近原则
        System.out.println("我的名字是 " + name);
        System.out.println("我的年龄是 " + age); // 5
        System.out.println("我的身高是 " + height);
        System.out.println("我的体重是 " + weight);
        System.out.println("我的性别是 " + sex);
        System.out.println("我的爱好是 " + hobby);
    }

    public static void main(String[] args) {
        // 创建一个 实例对象
        // 格式:类名 对象名 =  new 类名();
        Vtuber sakuna = new Vtuber();
        // 给实例属性赋值 使用对象名访问属性 给属性赋值
        // 格式:对象名.属性名 = 值;
        sakuna.name = "yuuki sakuna";
        sakuna.age = 10000;
        // sakuna.sex = '女'; // 默认值为 null
        sakuna.height = 148;
        sakuna.weight = 44.5;
        sakuna.hobby = "Sing and game";
        // 使用对象名访问方法 格式:对象名.方法名();
        sakuna.singing();
        sakuna.gaming();
        sakuna.myInfo();
    }
}

构造方法

构造方法:用于创建对象的特殊方法,构造方法是用于属性初始化的。

基本语法

ts
构造方法格式:访问修饰符 +  类名(){}

特点作用

ts
特点:
	名称与类名完全相同。
	没有返回值类型。
	创建对象时,触发构造方法的调用,不可通过句点手动调用(普通方法的方式)
    
作用:构造方法是用于属性初始化的

应用:
	有参构造方法可以在创建对象的同时 给属性赋值 但并不是用来取代对象名加点的方式给属性赋值的
	实际开发中,我们只会书写两个构造方法,即可满足95%的开发场景:无参 和 全参构造

无参构造

ts
无参构造:
	如果没有在类中显式定义构造方法,则编译器(JVM)默认提供无参构造方法。
	如果定义了有参构造方法,则无参构造方法将会被覆盖,如需使用,必须显式书写。

注意:这些是成员变量(类的属性)在无参构造或未显式赋值时的默认值。 局部变量在 Java 中必须显式初始化,否则编译报错。

默认值

数据类型默认值
引用数据类型(如 String、数组、对象)null
整数类型(byte, short, int, long)0
浮点类型(float, double)0.0
字符类型(char)'\u0000'
布尔类型(boolean)false
java
package com.object;

public class Vtuber {
    // 实例变量 属性
    String name;
    int age;
    char sex;
    double weight;
    double height;
    String hobby;
    // 实例方法
    public void singing(){
        System.out.println("海想列车 只在梦中见过一点点~~~");
    }
    public void gaming(){
        System.out.println("Apex start!!!");
    }
    public void myInfo(){
        System.out.println("我的名字是 " + name);
        System.out.println("我的年龄是 " + age);
        System.out.println("我的身高是 " + height);
        System.out.println("我的体重是 " + weight);
        System.out.println("我的性别是 " + sex);
        System.out.println("我的爱好是 " + hobby);
    }
    // 构造方法 无参
    public Vtuber(){
        System.out.println("无参构造方法执行!");
    }
    // 构造方法 有参
    public Vtuber(String name,int age,double height,double weight,char sex,String hobby){
        System.out.println("有参构造方法执行!");
        this.name = name;
        this.age = age;
        this.height = height;
        this.weight = weight;
        this.sex = sex;
        this.hobby = hobby;
    }
    public static void main(String[] args) {
        // 格式:类名 对象名 =  new 类名();
        Vtuber sakuna = new Vtuber();
        // 给实例属性赋值 使用对象名访问属性 给属性赋值

    }
}

全参构造

ts
把需要的参数在初始化对象时,全部传入。
如果定义了有参构造方法,则无参构造方法将会被覆盖,如需使用,必须显式书写无参构造。
java
package com.object;

public class Vtuber {
    // 实例变量 属性
    String name;
    int age;
    char sex;
    double weight;
    double height;
    String hobby;
    // 实例方法
    public void singing(){
        System.out.println("海想列车 只在梦中见过一点点~~~");
    }
    public void gaming(){
        System.out.println("Apex start!!!");
    }
    public void myInfo(){
        System.out.println("我的名字是 " + name);
        System.out.println("我的年龄是 " + age);
        System.out.println("我的身高是 " + height);
        System.out.println("我的体重是 " + weight);
        System.out.println("我的性别是 " + sex);
        System.out.println("我的爱好是 " + hobby);
    }
    // 构造方法 无参
    public Vtuber(){
        System.out.println("无参构造方法执行!");
    }
    // 构造方法 有参
    public Vtuber(String name,int age,double height,double weight,char sex,String hobby){
        System.out.println("有参构造方法执行!");
        this.name = name;
        this.age = age;
        this.height = height;
        this.weight = weight;
        this.sex = sex;
        this.hobby = hobby;
    }
    public static void main(String[] args) {
        // 格式:类名 对象名 =  new 类名();
        Vtuber yousa = new Vtuber("泠鸢yousa",18,148,45,'女',"Sing and Stream");
        // 调用方法
        yousa.myInfo();
    }
}
java
package com.object;

public class Singer {
    String name;
    char sex;
    int age;
    String works;
    String interest;
    String constellation;

    public void sing(){
        System.out.println("浪奔~浪流~万里涛涛江水永不休~");
    }
    public void showWorks(){
        System.out.println(name + " 的作品有 " + works);
    }
    public Singer(){

    }
    public Singer(String n,int a,char s,String w,String i,String c){
        // 这些是赋值给类中的属性
        name = n;
        age = a;
        sex = s;
        works = w;
        interest = i;
        constellation = c;
    }
    public static void main(String[] args) {
        Singer singer = new Singer();
        // 赋值
        singer.name = "yeliyi";
        singer.age = 40;
        singer.sex = '女';
        singer.works = "上海滩";
        singer.interest = "唱歌,高尔夫";
        singer.constellation = "天秤座";
        // 访问方法
        singer.sing();
        singer.showWorks();
        // 新增一个实例
        Singer singer1 = new Singer("yousa",18,'女',"勾指起誓","唱歌","天蝎座");
        singer1.showWorks();
    }
}

实际开发中,只会写两个构造方法,一个无参,一个全参。

关于无参构造:如果没有在类中显示定义构造方法,则编译器默认提供无参构造方法。

如果定义了有参构造方法,则无参构造方法将会被覆盖,如需使用,必须显式书写。

构造方法重载

同一个类中的构造方法 参数列表不同

java
    // 构造方法 有参
    public Vtuber(String name,int age){
        System.out.println("有参构造方法one 执行!");
        this.name = name;
        this.age = age;
    }
    // 构造方法 有参 构造方法重载
    public Vtuber(double height,double weight,char sex,String hobby){
        System.out.println("有参构造方法two 执行!");
        this.height = height;
        this.weight = weight;
        this.sex = sex;
        this.hobby = hobby;
    }
    public static void main(String[] args) {
        // 格式:类名 对象名 =  new 类名();
        Vtuber yousa = new Vtuber("泠鸢yousa",18);
        // 调用方法
        yousa.myInfo();
    }

this关键字

问题背景

ts
为了解决当实例方法的形参和实例变量一样时,无法赋值的问题。

局部变量出现了重名->就会使用就近原则->使用this关键字指向实例

this关键字:this 表示当前对象指当前正在使用的对象

以学生类 class 为例

特征--属性:姓名、年龄、性别、身高、体重、爱好、联系方式、学号

行为--方法:学习 吃饭 睡觉 ……

this关键字:this 表示当前对象 当前正在使用的对象

this可以访问本类中的

​ 实例属性:this.属性名

​ 实例方法: this.方法名()或方法名() 也可以直接书写方法名调用 两种方式没有任何差异

​ 构造方法: 通过 this(实参列表) 调用本类中的构造方法。

java
例如:使用 this() 表示调用调用本类中的无参构造方法。使用 this(name,age) 调用本类中的有参构造方法,根据参数的数量顺序类型匹配有参构造方法匹配不到编译会出错

注意

ts
this(实参) 调用构造方法,必须在本类构造方法中的第一句,并且访问构造只能有一个。

public Singer(String name,int age,char sex){
        this.name = name;
        this.age = age;
        this.sex = sex;
    }
public Singer(String name,int age,char sex,String works,String interest,String constellation){
    // 调用上边的构造方法
    this(name,age,sex);
    this.works = works;
    this.interest = interest;
    this.constellation = constellation;
}

示例

this访问实例属性

java
// 为了解决 构造方法中的形参和实例变量一样时,无法赋值的问题。


package com.object;

public class Vtuber {
    // 实例变量 属性
    String name;
    int age;
    char sex;
    double weight;
    double height;
    String hobby;
    // 实例方法
    public void singing(){
        System.out.println("海想列车 只在梦中见过一点点~~~");
    }
    public void gaming(){
        System.out.println("Apex start!!!");
    }
    public void myInfo(){
        // 调用实例方法 方式1 通过this.
        this.gaming();
        // 调用实例方法 方式2 直接调用
        singing();
        System.out.println("我的名字是 " + this.name); // 和直接写 name 效果是一样的
        System.out.println("我的年龄是 " + age);
        System.out.println("我的身高是 " + height);
        System.out.println("我的体重是 " + weight);
        System.out.println("我的性别是 " + sex);
        System.out.println("我的爱好是 " + hobby);
    }
    // 构造方法 无参
    public Vtuber(){
        System.out.println("无参构造方法执行!");
    }
    // 构造方法 有参
    public Vtuber(String name,int age){
        System.out.println("有参构造方法one 执行!");
        this.name = name;
        this.age = age;
    }
    // 构造方法 有参 构造方法重载
    public Vtuber(double height,double weight,char sex,String hobby){
        System.out.println("有参构造方法two 执行!");
        this.height = height;
        this.weight = weight;
        this.sex = sex;
        this.hobby = hobby;
    }
    public static void main(String[] args) {
        // 格式:类名 对象名 =  new 类名();
        Vtuber yousa = new Vtuber("泠鸢yousa",18);
        // 调用方法
        yousa.myInfo();
    }
}

this访问实例方法

java
package com.object;

public class Vtuber {
    // 实例变量 属性
    String name;
    int age;
    char sex;
    double weight;
    double height;
    String hobby;
    // 实例方法
    public void singing(){
        System.out.println("海想列车 只在梦中见过一点点~~~");
    }
    public void gaming(){
        System.out.println("Apex start!!!");
    }
    public void myInfo(){
        // 调用实例方法 方式1 通过this.
        this.gaming();
        // 调用实例方法 方式2 直接调用
        singing();
        System.out.println("我的名字是 " + name);
        System.out.println("我的年龄是 " + age);
        System.out.println("我的身高是 " + height);
        System.out.println("我的体重是 " + weight);
        System.out.println("我的性别是 " + sex);
        System.out.println("我的爱好是 " + hobby);
    }
    // 构造方法 无参
    public Vtuber(){
        System.out.println("无参构造方法执行!");
    }
    // 构造方法 有参
    public Vtuber(String name,int age){
        System.out.println("有参构造方法one 执行!");
        this.name = name;
        this.age = age;
    }
    // 构造方法 有参 构造方法重载
    public Vtuber(double height,double weight,char sex,String hobby){
        System.out.println("有参构造方法two 执行!");
        this.height = height;
        this.weight = weight;
        this.sex = sex;
        this.hobby = hobby;
    }
    public static void main(String[] args) {
        // 格式:类名 对象名 =  new 类名();
        Vtuber yousa = new Vtuber("泠鸢yousa",18);
        // 调用方法
        yousa.myInfo();
    }
}

this访问构造方法

java
package com.object;

public class Vtuber {
    // 实例变量 属性
    String name;
    int age;
    char sex;
    double weight;
    double height;
    String hobby;
    // 实例方法
    public void singing(){
        System.out.println("海想列车 只在梦中见过一点点~~~");
    }
    public void gaming(){
        System.out.println("Apex start!!!");
    }
    public void myInfo(){
        // 调用实例方法 方式1 通过this.
        this.gaming();
        // 调用实例方法 方式2 直接调用
        singing();
        System.out.println("我的名字是 " + name);
        System.out.println("我的年龄是 " + age);
        System.out.println("我的身高是 " + height);
        System.out.println("我的体重是 " + weight);
        System.out.println("我的性别是 " + sex);
        System.out.println("我的爱好是 " + hobby);
    }
    // 构造方法 无参
    public Vtuber(){
        System.out.println("无参构造方法执行!");
    }
    // 构造方法 有参
    public Vtuber(String name,int age){
        System.out.println("有参构造方法one 执行!");
        this.name = name;
        this.age = age;
    }
    // 构造方法 有参 构造方法重载
    public Vtuber(double height,double weight,char sex,String hobby){
        // 出现了重复的代码,就可以直接调用之前的构造方法
        // 访问构造方法,通过参数的数量顺序类型来匹配构造方法,匹配不到编译会出错
        this("yousa",18);
        System.out.println("有参构造方法two 执行!");
        this.height = height;
        this.weight = weight;
        this.sex = sex;
        this.hobby = hobby;
    }
    public static void main(String[] args) {
        // 格式:类名 对象名 =  new 类名();
        Vtuber yousa = new Vtuber(148,45,'女',"Sing and Stream");
        // 调用方法
        yousa.myInfo();
    }
}

this在构造方法和实例方法中的参数中隐式定义了一个this参数,这个this参数的类型是本类类型

方法中参数 this 的设置是JVM设计时定义的

可以通过 javap 反编译命令查看

示例:this形参的示例

java

没有super,是因为super是包含在this之中的。

静态方法中的形参,没有添加 this隐式参数,所以无法使用this和super