java全端课2--java-面向对象(上)

方法

声明的格式:

arduino 复制代码
public class 类名{
    【修饰符】 返回值类型  方法名(【形参列表】){
        方法体语句;
    }
}

//【】表示可选

方法调用过程内存分析

  • 入栈:当方法被调用执行时,JVM会给这个方法在"栈"内存开辟一块独立的内存空间,用于存储这个方法的局部变量等信息。
  • 出栈:当这个方法调用结束,JVM会自动释放这个方法占用的栈内存空间。
  • (栈:先进后出)

方法的参数传递机制

  1. 参数是基本数据类型 结论:参数是基本数据类型时,实参把数据值copy给形参之后,它们就没关系了。形参无论怎么修改,都与实参无关。
  2. 参数是引用数据类型 Java的类,数组等都是引用数据类型,参数是引用数据类型(8种基本数据类型以外),实参给形参的是首地址的副本,意味着形参和实参指向同一个对象,所以形参的修改会影响实参。
  3. 凡是new操作的都在堆。
  4. 出栈释放的是栈内存空间,不会自动释放堆内存空间。

快捷键

  1. 生成main方法
  • main + 回车
  • psvm + 回车
  1. 变量大于
  • soutv: 默认输出离它最近的变量的值
  • 变量.soutv:输出对应变量的值

方法的重载

  1. 方法的重载:

在同一个类中,出现两个方法的名称相同,形参列表不同,这样的形式称为方法的重载。方法重载与修饰符、返回值类型、方法体无关。

形参列表不同:可以是个数不同,类型不同,顺序不同,不看形参名

  1. 为什么要重载?

方法名见名知意,如果两个方法的功能是相同的,那么它的名称就应该一样

  1. 重载方法的调用原则

先找实参的个数、类型、顺序与形参完全匹配的,如果找到了,就可以确定了 如果没找到完全匹配的,要找可以兼容的,大的类型可以兼容小的类型,例如double可以兼容int

调用重载的方法时,光标至于括号中,Ctrl+P 可查看所匹配的方法参数类型。

可变参数

可变参数是指参数的个数不确定,可以是0~n个参数值。

可变参数的标记符号:...

可变参数的使用方式,用使用数组的方式使用它即可。

可变参数 数组类型
形式(以int为例) int... int[]
调用时 可以传入0~n个元素,也可以直接传入数组 只能传入数组
限制 一个方法最多只能有1个可变参数,而且必须是最后一个形参 没有限制

面向对象的基本概念

1.1 什么是面向对象?

面向对象是一种编程的思想,编程的方式。

面向过程是另一种非常经典的编程思想。

面向过程是以步骤/过程为中心,面向对象是以类和对象为中心。

举例:把大象装进冰箱的代码实现

面向过程:

  • 第一步:把冰箱门打开
  • 第二步:把大象装进去
  • 第三步:把冰箱门关上

面向对象:

角色/对象:人、冰箱、大象

每一个角色需要完成什么事,能干什么事,或具有什么功能:

  • 人:推和拉的能力
  • 大象:走
  • 冰箱:打开,关上,冷冻...
java 复制代码
public class 人{
    public void 推(东西){
        //....
    }
    public void 拉(东西){
        //....
    }
}
java 复制代码
public class 大象{
    public void 走(){
        //...
    }
}
java 复制代码
public class 冰箱{
    public void 打开(){
        //...
    }
    public void 关上(){
        //...
    }
    public void 冷冻(){
        //...
    }
}
java 复制代码
public class 主类{
    public static void main(String[] args){
        人 ren = new 人("张三");
        大象 e = new 大象("亚洲", 10 );
        冰箱 b = new 冰箱("格力", 5,10,10);
        
        ren.拉(b);
        ren.拉(e);
        ren.推(e);
        ren.推(b);
    }
}

1.2 类与对象的概念

1、什么是类

生活中把事物也会进行分"类"。

Java中也要进行"分类",把一类具有相同特性/特征的事物用一个Java来描述。例如:

要做一个学生考试管理系统,学生:张三、李四、王五等,他们的共同特征:

  • 数据特征:姓名、年龄、性别、身份号码.... => 类的属性
  • 行为特征:注册、登录、考试、查看成绩... => 类的方法

总结:一类具有相同特性的事物的抽象描述。

2、什么是对象

对象是指这类事物的一个具体的个体,实体。

3、类与对象的关系

类是创建对象的模板,设计图。比喻:造汽车,先有汽车的设计图。设计图中体现了这里车的所有特征/构造/结构和功能。

对象是具体的实例,个体。比喻:对象是具体的一辆车,能开的车。

1.3 如何声明类和创建对象?

先有类还是先有对象?

从需求分析/设计项目的角度:先观察对象,才能总结有哪些类?

从代码实现的角度来说:先声明类,后创建对象。

1、声明类的格式

java 复制代码
【修饰符】 class 类名{
    
}

public的类有一个要求,类名与xx.java的源文件名必须一致。

类名:见名知意。遵循大驼峰命名法,即每一个单词首字母大写。

java 复制代码
public class Student {
}

2、创建对象的格式

java 复制代码
类名 对象名 = new 类名();

new是用来创建实例对象的关键字,实际意义是在堆中开辟一块内存用于存储对象的信息。例如:创建数组对象时,在堆中开辟一块空间,用来存储数组的元素。

java 复制代码
public class TestStudent {//主类,包含主方法的类
    public static void main(String[] args) {
        Student s1 = new Student();
        Student s2 = new Student();
        Student s3 = new Student();

        System.out.println(s1);//Student@4eec7777
        System.out.println(s2);//Student@3b07d329
        System.out.println(s3);//Student@41629346
        //s1,s2,s3都是引用数据类型的变量,s1,s2,s3中都是存储对象的首地址。
        //这一点与数组一样

        int[] arr = {1,2,3,4};
        System.out.println(arr);//[I@404b9385
    }
}

Student是一个类,也是一种数据类型,称为类类型。它与String是一样的。只不过String是JRE核心类库中已经提前写好的类,Student是咱们自己写的类。同理,数组类型,例如:int[],String[],double[]也是数据类型,是数组类型。它们统统都是引用数据类型。

1.4 包

1.4.1 包的作用

  • 可以通过不同的文件夹/包帮我们管理众多的类,分门别类进行管理,便于后期的维护
  • 可以避免类的重名,有了包之后,类的全名称就是包.类名
  • 包结合权限修饰符(public,protected,缺省,private等)来限定类或成员可见性范围。关于权限修饰符后面再讲。

1.4.2 如何声明包?

java 复制代码
package 包名;
  • 这句代码必须在源文件的首行。
  • 包名的命名规范:所有单词都小写,单词直接使用.分割。习惯上用公司域名倒置的写法,例如:com.123vwu.xxx

1.4.3 如何跨包使用类

  • 如果是同一个包,类之间互相使用,不需要import
  • 如果是跨包(不同包),类之间互相使用,必须import 或 使用类的全名称
  • 只有public修饰的类才能跨包使用
  • java.lang包的类,在任意地方使用都不需要导包,例如:String,Math,System 它们都是java.lang包的类
  • 如果需要导入不同包中的相同类名,只能一个是 import,一个是全名称,或者两个都全名称

1.5 类的成员之一:成员变量

1.5.1 成员变量的声明格式

java 复制代码
【修饰符】 class 类名{
    【修饰符】 数据类型 变量名;
}

成员变量的声明位置:类中方法外。

如果把变量定义/声明到方法里面,那就是局部变量,不是成员变量。

【修饰符】:暂时都是public

1.5.2 成员变量的分类

1、静态变量

静态变量不依赖于对象,不属于对象,属于类。跨类使用它,建议通过"类名.静态变量"。也可以通过"对象.静态变量"。

2、实例变量/非静态成员变量

实例变量依赖于对象,属于对象。跨类使用它,必须通过"对象.实例变量"。

对于静态变量的跨类访问,建议用类名.静态变量 如果用对象.静态变量,编译能通过,不会报错。 但是:1. 容易误导其他开发人员,错误理解成访问的是实例变量。2. 给编译器增加工作量,编译器最终还是需要翻译成类名.静态变量.

1.5.3 成员变量的特点

1、成员变量有默认值
类型 默认值
byte 0
short 0
int 0
long 0L
float 0.0F
double 0.0
char '\u0000'
boolean false
String等类、数组等引用数据类型 null
2、是否共享性特点

静态变量的值是所有对象共享的,因为它属于类,而类是创建对象模板。

实例变量的值是每一个对象独立的,因为它属于某个对象。

问:成员变量该不该加static?

原则:看这个成员变量的值是不是所有对象共享的,只存一份的,如果是,就应该是静态的,否则就不能是静态的。

1.5.4 示例代码

java 复制代码
package com.test.field;

public class Teacher {
    //静态变量,静态成员变量,学校名是所有老师共享的
    public static String school;

    //实例变量,非静态成员变量,姓名、年龄、薪资是每一个老师独立的
    public String name;//姓名
    public int age;//年龄
    public double salary;//薪资
}
java 复制代码
package com.test.field;

public class TestTeacher {
    public static void main(String[] args) {
//        System.out.println("姓名:" + name);//错误,name在Teacher类中
       // System.out.println("姓名:" + Teacher.name);//错误,因为name没有static

        System.out.println("学校:" + Teacher.school);//null

        Teacher t1 = new Teacher();//创建对象,创建实例
        System.out.println("t1的姓名:" + t1.name);//null
        System.out.println("t1的年龄:" + t1.age);//0
        System.out.println("t1的薪资:" + t1.salary);//0.0

//        int a;//局部变量
//        System.out.println("a = " + a);//报错,因为a没有初始化

        System.out.println("赋值之前:");

        Teacher.school = "大学";
        t1.name = "张三";
        t1.age = 23;
        t1.salary = 16500;

        Teacher t2 = new Teacher();
        t2.school = "微客鸟窝";//推荐用 Teacher.school = "微客鸟窝";

        System.out.println("t1的学校:" + t1.school);//推荐用 Teacher.school
        System.out.println("t1的姓名:" + t1.name);
        System.out.println("t1的年龄:" + t1.age);
        System.out.println("t1的薪资:" + t1.salary);

        System.out.println("t2的学校:" + t2.school);//推荐用 Teacher.school
        System.out.println("t2的姓名:" + t2.name);
        System.out.println("t2的年龄:" + t2.age);
        System.out.println("t2的薪资:" + t2.salary);

    }
}
java 复制代码
package com.test.field;

public class Chinese {//中国人
    //国家名是所有中国人共享的,所以是静态的
    private static String country;
    
    //每一个中国人的名字是独立的,所以是非静态的
    private String name;
}
java 复制代码
package com.test.field;

public class Account {//银行账号
    //银行利率是大家统一的,所以是静态的
    private static double rate;//利率
    
    //余额是每个人不同的,所以是非静态的
    private double balance;//余额
}

1.5.5 引用数据类型的成员变量

java 复制代码
package com.test.field;

public class Husband {//丈夫
    //以下是两个引用数据类型的实例变量
    public String name;
    public Wife wife;
}
java 复制代码
package com.test.field;

public class Wife {//妻子
    //以下是两个引用数据类型的实例变量
    public String name;
    public Husband husband;
}
java 复制代码
package com.test.field;

public class TestHusbandWife {//主类,测试类
    public static void main(String[] args) {
        Husband h = new Husband();
        h.name = "张三";

        Wife w = new Wife();
        w.name = "翠花";

        h.wife = w;//给h.wife变量赋值一个Wife类型的对象
        w.husband = h;

        System.out.println("丈夫的姓名:" + h.name +",他妻子的姓名:" + h.wife.name);
        System.out.println("妻子的姓名:" + w.name +",她的丈夫的姓名:" + w.husband.name);
    }
}

1.6 类的成员之二:成员方法

1.6.1 成员方法的声明格式

java 复制代码
【修饰符】 class 类名{
  【修饰符】 返回值类型 方法名(【形参列表】){
    方法体语句;
  }
}

1.6.2 成员方法的分类

  1. 静态方法
  • 态方法中,只可以访问本类的静态成员,包括本类的静态方法和静态变量。
  • 跨类调用静态方法,建议使用"类名.静态方法",当然也可以通过"对象.静态方法"。
  1. 实例方法/非静态方法
  • 实例方法中,可以访问本类的所有成员,包括本类的静态成员和非静态成员。
  • 跨类调用非静态方法/实例方法,只可以通过"对象.非静态方法"的方式。

问:什么时候用静态方法,什么时候用非静态方法呢?

答:原则,如果在方法体中,需要访问本类的非静态成员,那么这个方法只能是非静态的。

相关推荐
撸猫79127 分钟前
HttpSession 的运行原理
前端·后端·cookie·httpsession
嘵奇1 小时前
Spring Boot中HTTP连接池的配置与优化实践
spring boot·后端·http
子燕若水1 小时前
Flask 调试的时候进入main函数两次
后端·python·flask
程序员爱钓鱼1 小时前
跳转语句:break、continue、goto -《Go语言实战指南》
开发语言·后端·golang·go1.19
Persistence___2 小时前
SpringBoot中的拦截器
java·spring boot·后端
嘵奇2 小时前
Spring Boot 跨域问题全解:原理、解决方案与最佳实践
java·spring boot·后端
景天科技苑4 小时前
【Rust泛型】Rust泛型使用详解与应用场景
开发语言·后端·rust·泛型·rust泛型
lgily-12256 小时前
常用的设计模式详解
java·后端·python·设计模式
意倾城7 小时前
Spring Boot 配置文件敏感信息加密:Jasypt 实战
java·spring boot·后端
火皇4057 小时前
Spring Boot 使用 OSHI 实现系统运行状态监控接口
java·spring boot·后端