开发方法:
结构化开发
● 面向功能划分软件结构
● 自顶向下
● 最小的子系统是方法
● 制约了软件的可维护性和可扩展性
面向对象开发(面向对象程序设计OOP)
● 把软件系统看成各种对象的集合
● 系统结构较稳定
● 子系统相对独立
● 软件可重用性、可维护性和可扩展性强
1 面向对象
1.1 几个概念(类、对象、属性、方法)
类,指的是将所有实体看为对象,实体共同的部分抽象为类。
即 具有相同属性和方法的一组对象的集合。(共同特征的描述)
由关键字class修饰,代表一个自定义类。
对象(具体实例):用来描述客观事物的一个实体,由一组属性和方法构成。
属性:对象具有的各种特征(静态的)。每个对象的每个属性都拥有特定值。
方法(method):对象执行的操作,是程序中最小的执行单元。方法里的代码要么全都执行,要么全都不执行。
重复的代码或具有独立功能的代码可以抽取到方法中,提高代码的复用性和可维护性。
例:“小狗”这个对象的属性和方法
属性:颜色(黑色)
方法:教、跑、吃
1.2 类和对象的关系
类是对象的抽象,对象是类的具体实现/实例。
类 对象名=new 类(); -------创建对象
对象名.属性、对象名.方法() -----------访问类的内部,类的属性和方法由对象名. 来调用
2 类
在Java中,必须先设计类,才能获得对象。
类(设计图):是对象共同特征的描述。
一个.java文件可以定义多个class类,但只能有一个类由public修饰(主类),且主类名与文件名一致。(实际开发中建议还是一个文件定义一个class类。)
2.1 类的定义
public class 类名{ // 类名首字母建议大写,驼峰模式,要见名知意。
1. 成员变量(代表属性,一般是名词)
2. 成员方法(代表行为,一般是动词)
3. 构造器(后面学习)
4. 代码块(后面学习)
5. 内部类(后面学习)
}
类名 对象名 = new 类名();
定义一个手机类
public class Phone{// 类名是Phone,全限定类名是 包名.Phone
// 没有main方法,不能运行
// 属性(成员变量)
// 一般来说只做声明不做赋值
String brand;
double price;
//行为(方法)
public void call(){
System.out.println("手机在打电话");
}
public void playGame(){
System.out.println("手机在玩游戏");
}
}
定义一个测试类
public class PhoneTest{
public static void main(String[] args) {
//创建手机对象
Phone p = new Phone();
//给手机赋值
p.brand = "小米";
p.price = 1999.98;
//获取手机对象的值
System.out.println(p.brand);
System.out.println(p.price);
//调用手机中的方法
p.call();
p.playGame();
//第二部手机
Phone p2 = new Phone();
p.brand = "苹果";
p.price = 8999;
}
}
运行结果:
2.2 JavaBean类
现在我们所学的类,专业术语叫做 Javabean类,是用来描述一类事物的类。面向对象-06-标准的javabean类_哔哩哔哩_bilibili
javaBean类中是不写main方法的,
之前我们所编写的含有main方法的类,叫做 测试类。
3 属性
属性,又叫成员变量、对象变量。
3.1 成员变量
成员变量的完整定义格式:
修饰符 数据类型 变量名称 = 初始化值
一般我们只定义不给值,会有默认值。
类是描述对象的,并不具体,创建对象之后有了特定的对象再给值。
3.2 局部变量
局部变量的作用域是该变量被声明的作用域(最贴近的花括号范围)。
成员变量的作用域是整个类。
3.3 成员变量和局部变量的区别
如果成员变量和局部变量同名,则 变量名指向局部变量(就近原则)
此时如果要打印成员变量,应该用this.变量名来指向成员变量。
成员变量有对应类型的默认值,而局部变量没有默认值,如果没有初始化,就会编译报错。
4 方法
4.1 方法定义的规则
4.2 方法的分类
方法分为有返回值和无返回值方法:
返回值类型为void,表示该方法没有返回值
- 主要关注执行过程,可以省略return语句不写;
- 如果要编写return,后面不能跟具体数据。
return;//表示结束方法
返回值类型为具体数据类型,表示该方法有返回值
- 必须有return语句,且return语句返回的值必须能被返回值类型接收,在方法调用处应该有对应的变量接收。
return 数据; // 表示结束方法和返回结果
案例(注意成员变量、成员方法的应用):
/**
* 演示加法运算
*/
public class Add {// 类名是Add ,全限定类名是 包名.Add
int x;//属性,又叫成员变量、对象变量
int y;
public int sum(){//方法,又叫成员方法、对象方法
return x+y;//有返回值
}
public static void main(String[] args) {
Add a=new Add();
a.x=10;
a.y=20;
int res=a.sum();//调用sum()方法,返回值赋值给res
System.out.println(res); // 打印res
}
}
运行结果:
30
4.3 方法的几个注意项
- return语句下面不能编写代码,因为return表示结束方法,后面的代码永远不会执行到,属于无效代码。
- 方法和方法之间是平级关系,不能相互嵌套。
- 方法的编写顺序和执行顺序无关。
- 方法不调用就不执行。
4.4 方法调用
方法调用:用对象名.方法名(实参列表); ------实参列表要和形参列表类型完全对应。
方法之间允许相互调用,不需要知道方法的具体实现,实现重用,提高效率。
调用同一个对象的方法:
public class Function {
void a(){
System.out.println("这是a方法");
}
void b(){
a();
System.out.println("这是b方法");
}
public static void main(String[] args) {
Function f=new Function();
f.b();
}
}
运行结果:
这是a方法
这是b方法
调用不同对象的方法:
public class Function {
void a(){
System.out.println("这是a方法");
}
void b(){
a();
System.out.println("这是b方法");
Add d=new Add();//成员方法要用对象名字调用
System.out.println(d.sum());//sum()方法是有返回值的,要么定义一个变量接收返回值,要么直接打印,此为直接打印
}
public static void main(String[] args) {
Function f=new Function();
f.b();
}
}
运行结果:
这是a方法
这是b方法
0
4.5 方法重载
方法重载的规则:
1、在同一类中(从父类继承的也算)
2、方法名相同
3、形参列表不同(参数个数不同、参数顺序不同、参数类型不同)
[4、和访问修饰符、返回值类型无关]
好处:定义方法的时候不用太多的单词,减少调用方法时的麻烦
public class Add{
public static int sum(int a, int b) {
return a+b;
}
public static int sum(int a,int b,int c){
return a+b+c;
}
}
4.6 方法重写@Override
方法重写的规则:(mv 5.4 08.35.22 - 0:53:20)
1、两个类有继承关系
2、方法名相同
3、参数列表相同
4、访问修饰符的范围必须大于等于父类(public>protected>空着不写)
5、返回值类型必须小于父类
6、抛出的异常范围不嫩比父类更严格(异常范围不能扩大)
7、只有被添加到虚方法表中的方法才能被重写
可以被重写的方法都可以称作虚方法 :不用static、final、private修饰的方法。
public class Test {
public static void main(String[] args) {
OverseasStudent s = new OverseasStudent();
s.lunch();
}
}
class Person{
public void eat(){
System.out.println("吃米饭,吃菜");
}
public void drink(){
System.out.println("喝开水");
}
}
class OverseasStudent extends Person{
public void lunch(){
this.eat();
this.drink();
super.eat();
super.drink();
}
@Override
public void eat() {
System.out.println("吃意大利面");
}
@Override
public void drink() {
System.out.println("喝凉水");
}
}
运行结果:
吃意大利面
喝凉水
吃米饭,吃菜
喝开水
重写equals()方法的几个关键点
==比较的是地址,equals()是基类Object自带的方法,可以重写它也可以不重写:
没有重写equals()方法时,equals()等同于==。此时比较的是地址。
Java.lang.String重写了equals()方法,把equals()的判断变为了判断其值,equals()就不等同于==了。此时比较的是值(内容)。
(05-04 08.35.22 2:41:00)
1、用instanceof关键字判断类型是否一致
2、类型一致后,用强制类型转换,将一个object类型转成具体类型
小类型接收大类型,需要强制类型转换
大类型接收小类型,会默认转换成大类型
注意: (非基本类型: 小类型和大类型必须有父子关系)
3、根据业务需要、进行判断
instanceof 是 Java 的一个二元操作符,类似于 ==,>,< 等操作符。
instanceof 是 Java 的保留关键字。它的作用是测试它左边(引用类型所引用的)对象是否是它右边的类的实例,返回 boolean 的数据类型。
4.7 方法重载和重写的区别
重载是为了实现同一个功能的不同场景
重写是多态的基础,为了解决在不同类型中的同一个功能有不同的表现
4.8 构造方法
构造方法也叫构造器、构造函数。面向对象-05-构造方法_哔哩哔哩_bilibili
每一个类都默认有一个来自Object类的空参构造方法,格式如下:
public 类型名() { } //方法体为空,功能:创建对象
作用:在创建对象的时候给成员变量进行赋值。
特点:1. 方法名与类名相同,大小写也要一致
2. 没有返回值类型,连void都没有
3. 没有具体的返回值,不能由return带回结果数据
执行时机:
构造方法是不能手动调用的,而是在创建对象的时候由虚拟机自动调用;
每创建一次对象,就会调用一次构造方法。
构造方法有无参构造和有参构造:
无参构造:初始化的对象时,成员变量的数据均采用默认值
有参构造:在初始化对象的时候,同时可以为对象进行赋值
一旦我们自定义了有参构造,原来的无参构造系统就不再自动提供,
因此在定义有参构造的同时,应该自主 显式的定义无参构造。
public 类型名(形参列表){
//代码
}
public 类型名() { }
一旦自定义有参构造后一定要再手动添加一个无参构造!!!
推荐使用的方式:无论是否使用,都手动书写无参构造方法和带全部参数(父类+子类)的构造方法
有参构造快捷键:Alt+Insert---constructor 或右键Generate---constructor
调用的时候:类型名 对象名=new 类型名(实参列表);
public class Student {
int stuNo;
String stuName;
String gender;
int age;
double score;
public Student(){}//无参构造方法
public Student(String name,double score){//有参构造方法
this.name=name;//this代表当前对象,成员变量成员方法都需要用对象名调用,这里的this就代替了对象名
this.score=score;
}
}
//调用时
Student stu=new Student("张三",80);
注意以上代码中的this关键字
5 传值和传地址的区别
5.1 传值
基本数据类型之间传递的是值,改变一个变量的值,不会改变另一个变量的值
int a=1;
int b=a;
b++;//b的值+1,但a的值不会变
----------------------------------
public class A(int num){
num=num+1;
}
int a=4;
A(a);
System.out.println(a);//此时a的值还是4
5.2 传地址
引用类型的变量传递的是地址(对象的引用),修改一个对象中的属性值,会同步到其他引用中
Student a=new Student();
Student b=a;
b.age=10;//此时a.age也是10
b=new Student();
b.age=18;//此时因为地址改变,不会影响到a.age