【JavaSE学习】Day4JavaSE面向对象 (上) 看这三篇就够了

 系列文章目录

        Day1 JavaSE环境配置
        Day2 JavaSE基础语法
        Day3 JavaSE数组
        Day4 JavaSE面向对象(上)
        Day5 JavaSE面向对象(中)
        Day6 JavaSE面向对象(下)
        Day7 JavaSE面向对象 
        Day8 JavaSE异常处理
        Day9 JavaSE多线程
        Day10 JavaSE集合
        Day11 JavaSE泛类
        Day12 JavaSEIO流
        Day13 JavaSE反射

文章目录


前言

        上期讲述了JavaSE数组的使用和常见用法和异常,本期主要来讲述JavaSE面向对象和类,内容有点多,大家聚精会神听我说。


以下是本篇文章正文内容

 一、类与对象📚

面向对象学习的三条主线📕

  •  Java类及类的成员:属性、方法、构造器;代码块、内部类 
  •  面向对象的大特征:封装性、继承性、多态性、(抽象性) 
  •  其它关键字:this、super、static、final、abstract、interface、package、import等
     

面向对象与面向过程(理解)📕

  • 面向过程:强调的是功能行为,以函数为最小单位,考虑怎么做。
  • 面向对象:强调具备了功能的对象,以类/对象为最小单位,考虑谁来做。举例对比:人把大象装进冰箱。
  • 面向对象中两个重要的概念:类:对一类事物的描述,是抽象的、概念上的定义对象:是实际存在的该类事物的每个个体,因而也称为实例(instance)
  •   >面向对象程序设计的重点是类的设计
  •   >设计类,就是设计类的成员。

二者的关系:📚
对象,是由类new出来的,派生出来的。
面向对象思想落地实现的规则一💡

  • 创建类,设计类的成员
  • 创建类的对象
  • 通过“对象.属性”或“对象.方法”调用对象的结构

补充:几个概念的使用说明💡

  •  属性 = 成员变量 = field = 域、字段
  •  方法 = 成员方法 = 函数 = method
  •  创建类的对象 = 类的实例化 = 实例化类


对象的创建与对象的内存解析📕

Person p1 = new Person();
Person p2 = new Person();
Person p3 = p1;//没有新创建一个对象,共用一个堆空间中的对象实体。

如果创建了一个类的多个对象,则每个对象都独立的拥有一套类的属性。(非static的)
意味着:如果我们修改一个对象的属性a,则不影响另外一个对象属性a的值。

内存解析💡

 解释💡

编译完源程序以后,生成一个或多个字节码文件。
我们使用JVM中的类的加载器和解释器对生成的字节码文件进行解释运行。意味着,需要将字节码文件对应的类加载到内存中,涉及到内存解析。

虚拟机栈,即为平时提到的栈结构。我们将局部变量存储在栈结构中
堆,我们将new出来的结构(比如:数组、对象)加载在堆空间中。补充:对象的属性(非static的)加载在堆空间中。方法区:类的加载信息、常量池、静态域。


二、类的属性📚

类的设计中,两个重要结构之一:属性

属性  vs  局部变量📕

相同点💡

  • 定义变量的格式:数据类型  变量名 = 变量值
  • 先声明,后使用
  • 变量都其对应的作用域 

不同点💡

 在类中声明的位置的不同🖊    

  • 属性:直接定义在类的一对{}内             
  •  局部变量:声明在方法内、方法形参、代码块内、构造器形参、构造器内部的变量

 关于权限修饰符的不同🖊

  • 属性:可以在声明属性时,指明其权限,使用权限修饰符。
  • 常用的权限修饰符:private、public、缺省、protected  --->封装性。目前,大家声明属性时,都使用缺省就可以了。
  •  局部变量:不可以使用权限修饰符。

默认初始化值的情况🖊

  • 属性:类的属性,根据其类型,都默认初始化值。
  • 整型(byte、short、int、long:0)
  • 浮点型(float、double:0.0)
  • 字符型(char:0  (或'\u0000'))
  • 布尔型(boolean:false)
  • 引用数据类型(类、数组、接口:null)
  • 局部变量:没默认初始化值。意味着,我们在调用局部变量之前,一定要显式赋值。
  • 特别地:形参在调用时,我们赋值即可。

在内存中加载的位置🖊

  • 属性:加载到堆空间中   (非static)
  • 局部变量:加载到栈空间

三、类的方法📚

方法:类的设计中的重要结构,描述类应该具的功能。

方法的声明📕

权限修饰符  返回值类型  方法名(形参列表){
                      方法体
               }

    注意:static、final

举例:

  •  public void eat(){}
  •  public void sleep(int hour){}
  •  public String getName(){}
  •  public String getNation(String nation){}、abstract 来修饰的方法,后面再讲。

 说明:

  • 关于权限修饰符:默认方法的权限修饰符先都使用public
  • Java规定的4种权限修饰符:private、public、缺省、protected  -->封装性再细说 

return关键字📕

  • 使用范围:使用在方法体中

  • 作用:① 结束方法

  •            ② 针对于返回值类型的方法,使用"return 数据"方法返回所要的数据。

  • 注意点:return关键字后面不可以声明执行语句。

 有返回值  vs 没返回值📕

  • 如果方法返回值,则必须在方法声明时,指定返回值的类型。
  • 同时,方法中,需要使用return关键字来返回指定类型的变量或常量:“return 数据”。
  • 如果方法没返回值,则方法声明时,使用void来表示。通常,没返回值的方法中,就不需要使用return.但是,如果使用的话,只能“return;”表示结束此方法的意思。
  • 方法名:属于标识符,遵循标识符的规则和规范,“见名知意”。
  • 方法体:方法功能的体现。   
  • 方法的使用中,可以调用当前类的属性或方法。

方法的重载📕

方法的重载的概念💡

定义:

  • 在同一个类中,允许存在一个以上的同名方法,只要它们的参数个数或者参数类型不同即可。   

总结:"两同一不同"

  • 同一个类、相同方法名。
  • 参数列表不同:参数个数不同,参数类型不同

构成重载的举例💡

举例一:Arrays类中重载的sort() / binarySearch();PrintStream中的println()
举例二:如下的4个方法构成了重载

    public void getSum(int i,int j){
        System.out.println("1");
    }
    
    public void getSum(double d1,double d2){
        System.out.println("2");
    }
    
    public void getSum(String s ,int i){
        System.out.println("3");
    }
    
    public void getSum(int i,String s){
        System.out.println("4");
    }

不构成重载的举例💡

    //如下的3个方法不能与上述4个方法构成重载
   public int getSum(int i,int j){
           return 0;
   }
    
   public void getSum(int m,int n){
   
   }
    
   private void getSum(int i,int j){
       
   }

如何判断是否构成方法的重载💡

  • 严格按照定义判断:两同一不同。

  • 跟方法的权限修饰符、返回值类型、形参变量名、方法体都没关系!

如何确定类中某一个方法的调用💡

  • 方法名 ---> 参数列表

可变个形参的方法📕

举例说明💡

 public void show(int i){

 }
    
 public void show(String s){
     
     System.out.println("show(String)");
 
 }
    
 public void show(String ... strs){
        
     System.out.println("show(String ... strs)");
        
     for(int i = 0;i < strs.length;i++){
         
         System.out.println(strs[i]);
     
     }
 
 }

调用时💡

        test.show("hello");
        test.show("hello","world");
        test.show();
        test.show(new String[]{"AA","BB","CC"});

值传递机制📕

针对于方法内变量的赋值举例💡

        System.out.println("***********基本数据类型:****************");
        int m = 10;
        int n = m;
        
        System.out.println("m = " + m + ", n = " + n);
        
        n = 20;
        
        System.out.println("m = " + m + ", n = " + n);
        
        System.out.println("***********引用数据类型:****************");
        
        Order o1 = new Order();
        o1.orderId = 1001;
        
        Order o2 = o1;//赋值以后,o1和o2的地址值相同,都指向了堆空间中同一个对象实体。
        
        System.out.println("o1.orderId = " + o1.orderId + ",o2.orderId = " +o2.orderId);
        
        o2.orderId = 1002;
        
        System.out.println("o1.orderId = " + o1.orderId + ",o2.orderId = " +o2.orderId);
        

规则📕

  • 如果变量是基本数据类型,此时赋值的是变量所保存的数据值。
  • 如果变量是引用数据类型,此时赋值的是变量所保存的数据的地址值。

针对于方法的参数概念📕

  • 形参:方法定义时,声明的小括号内的参数
  • 实参:方法调用时,实际传递给形参的数据

值传递📕

  •  如果参数是基本数据类型,此时实参赋给形参的是实参真实存储的数据值。
  •  如果参数是引用数据类型,此时实参赋给形参的是实参存储数据的地址值。

典型例题与内存解析💡

四、面向对象的特征:封装性📚

面向对象的特征一:封装与隐藏📕

为什么要引入封装性💡

  • 我们程序设计追求“高内聚,低耦合”。
  • 高内聚 :类的内部数据操作细节自己完成,不允许外部干涉;
  • 低耦合 :仅对外暴露少量的方法用于使用。
  • 隐藏对象内部的复杂性,只对外公开简单的接口。便于外界调用,从而提高系统的可扩展性、可维护性。通俗的说,把该隐藏的隐藏起来,该暴露的暴露出来。这就是封装性的设计思想。


封装性思想具体的代码体现📕

  • 体现一:将类的属性xxx私化(private),同时,提供公共的(public)方法来获取(getXxx)和设置(setXxx)此属性的值
private double radius;
public void setRadius(double radius){
    this.radius = radius;
}
public double getRadius(){
    return radius;
}
  • 体现二:不对外暴露的私有的方法
  • 体现三:单例模式(将构造器私有化)
  • 体现四:如果不希望类在包外被调用,可以将类设置为缺省的。

Java规定的四种权限修饰符📕

  • 权限从小到大顺序为:private <  缺省 < protected < public
  • 具体的修饰范围:

  • 4种权限都可以用来修饰类的内部结构:属性、方法、构造器、内部类
  • 修饰类的话,只能使用:缺省、public


五、类的构造器📚

构造器的作用📕

  • 创建对象

  • 初始化对象的信息

使用说明💡

  • 如果没显式的定义类的构造器的话,则系统默认提供一个空参的构造器

  • 定义构造器的格式:权限修饰符  类名(形参列表){}

  • 一个类中定义的多个构造器,彼此构成重载

  • 一旦我们显式的定义了类的构造器之后,系统就不再提供默认的空参构造器

  • 一个类中,至少会有一个构造器。

举例

//构造器
    public Person(){
        System.out.println("Person().....");
    }
    
    public Person(String n){
        name = n;
        
    }
    
    public Person(String n,int a){
        name = n;
        age = a;
    }

六、this指针📚

可以调用的结构:属性、方法;构造器📕

  • this调用属性、方法:
  • this理解为:当前对象  或 当前正在创建的对象

在类的方法中,我们可以使用"this.属性"或"this.方法"的方式,调用当前对象属性或方法。但是,
通常情况下,我们都择省略"this."。
特殊情况下,如果方法的形参和类的属性同名时,我们必须显式的使用"this.变量"的方式,表明此变量是属性,而非形参。

在类的构造器中,我们可以使用"this.属性"或"this.方法"的方式,调用当前正在创建的对象属性或方法。但是,通常情况下,我们都择省略"this."。特殊情况下,如果构造器的形参和类的属性同名时,我们必须显式的使用"this.变量"的方式,表明此变量是属性,而非形参。

this调用构造器📕

  • ① 我们在类的构造器中,可以显式的使用"this(形参列表)"方式,调用本类中指定的其他构造器
  • ② 构造器中不能通过"this(形参列表)"方式调用自己
  • ③ 如果一个类中有n个构造器,则最多有 n - 1构造器中使用了"this(形参列表)"
  • ④ 规定:"this(形参列表)"必须声明在当前构造器的首行
  • ⑤ 构造器内部,最多只能声明一个"this(形参列表)",用来调用其他的构造器

七、属性赋值的顺序💡

  • ① 默认初始化
  • ② 显式初始化
  • ③ 构造器中初始化
  • ④ 通过"对象.方法" 或 "对象.属性"的方式,赋值
  • 以上操作的先后顺序:① - ② - ③ - ④  


总结

        本次文章讲述的是JavaSE面向对象与类(上),讲述的是初始类与对象、JVM中的内存结构、类的属性、属性和局部变量的对比、类的方法、方法的重载、可变个形参的方法、面向对象编程的封装性、类的构造器、this指针、属性赋值顺序等众多知识点,觉得文章帮助到你的,可以点点关注收藏起来,如果有疑问也可以评论区讨论。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

小小程序○

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值