Java_Day05学习
Object类被子类经常重写的方法
方法 | 说明 |
---|---|
toString() | 返回当前对象本身的有关信息,按字符串对象返回 |
equals() | 比较两个对象是否是同一个对象,是则返回****true |
hashCode() | 返回该对象的哈希代码值 |
getClass() | 获取当前对象所属的类信息,返回Class对象 |
Object类
Object类的 equals() 方法
比较两个对象是否是同一个对象,是则返回true
instanceof
用于判断一个引用类型所引用的对象是否是一个类的实例
可以用 instanceof 判断一个类是否实现了某个接口,也可以用它来判断一个实例对象是否属于一个类。instanceof 的语法格式为:
eg:
if (a instanceof Cat) { // 猫做的事情
Cat c = (Cat) a;
c.work();
对象 instanceof 类(或接口)
它的返回值是布尔型的,或真(true)、或假(false)。
多态
定义:多态就是指一个类实例的相同方法在不同情形有不同表现形式。
//同一个引用类型,使用不同的实例而执行不同操作
eg:
//父类的声明 对象 = new 子类的对象;
Person_homework test = new China_People();
//父类和子类中都存在的方法 最终执行的是子类的方法
test.work();
优点:
//频繁修改代码,代码可扩展性、可维护性差
多态就是同一个接口,使用不同的实例而执行不同操作
多态的三个条件:
继承的存在(继承是多态的基础,没有继承就没有多态);
子类重写父类的方法(多态下调用子类重写的方法);
父类引用变量指向子类对象(子类到父类的类型转换)。
子类转换成父类时的规则:
将一个父类的引用指向一个子类的对象,称为向上转型(upcasting),自动进行类型转换。
总结:
一、多态
1、定义:
1)生活中:同一事物,在不同环境下,表现出不同的形态
2)程序中:同一引用类型,传入不同的实例,会得到不同结果
2、多态的实现步骤:
1)子类继承父类
2)子类重写父类的方法
3)父类引用,传入子类实例
3、多态的两种表现形式
1)父类作为方法的参数出现
2)父类作为方法的返回值出现
4、引用类型之间转换
1)向上转型:直接转,即 父类 父对象=new 子类();
2)向下转型:强制转,即 子类 子对象=(父类)父对象;强制转换易引发ClassCastException,因此转换之前需判断类型是否匹配
if(obj instanceof 类)则进行转换
3)原因:子 is a 父; 父 has 子
5、多态的优点:提高代码的可扩展性
6、父类引用指向子类实例的注意事项
1)父类引用指向父类实例:父类 父对象=new 父类();可访问父类的允许访问成员
2)子类引用指向子类实例:子类 子对象=new 子类();可访问父类和子类的允许访问成员
3)父类引用指向子类实例:父类 父对象=new 子类();可以访问父类允许访问的成员;不允许访问子类特有成员;但如果子类重写了父类方法,则调用的是子类重写后的方法
多态的例子
public class TestAnimalDemo {
public static void main(String[] args) {
// 向上转型
Animal a = new Cat();
a.eat(); // 调用的是 Cat 的 eat
show(new Cat()); // 以 Cat 对象调用 show 方法
show(new Dog()); // 以 Dog 对象调用 show 方法
Cat c = (Cat) a; // 向下转型
c.work(); // 调用的是 Cat 的 work
}
/**
*
*/
public static void show(Animal a) {
a.eat();
// 类型判断
if (a instanceof Cat) { // 猫做的事情
Cat c = (Cat) a;
c.work();
} else if (a instanceof Dog) { // 狗做的事情
Dog c = (Dog) a;
c.work();
}
}
}
abstract class Animal {
abstract void eat();
}
class Cat extends Animal {
public void eat() {
System.out.println("吃鱼");
}
public void work() {
System.out.println("抓老鼠");
}
}
class Dog extends Animal {
public void eat() {
System.out.println("吃骨头");
}
public void work() {
System.out.println("看家");
}
}
输出:
吃鱼
抓老鼠
吃骨头
看家
吃鱼
抓老鼠
抽象类
1.定义:Java也可以创建一种类专门用来当作父类,这种类称为“抽象类”;
//抽象类的作用有点类似“模版”,其目的是要设计者依据它的格式来修改并创建新的类。但是并不能直接由抽象类创建对象,只能通过抽象类派生出新的类,再由它来创建对象。
eg:
abstract class 类名称 // 定义抽象类
{
声明数据成员;
访问权限 返回值的数据类型 方法名称(参数...)//定义一般方法
{
...
}
abstract 返回值的数据类型 方法名称(参数...);
//定义抽象方法,在抽象方法里,没有定义方法体
}
//但可以创建一个引用变量,其类型是一个抽象类,指向非抽象的子类实例
//普通类可以被实例化
2.规则:
//抽象类和抽象方法都必须用abstract关键字来修饰;
//抽象类不能被实例化,也就是不能用new关键字去产生对象;
//抽象方法只需声明,而不需实现;
//含有抽象方法的类必须被声明为抽象类,抽象类的子类必须复写所有的抽象方法后才 能被实例化,否则这个子类还是个抽象类。
2.抽象方法VS普通方法
有无方法体
3.抽象类与抽象方法的使用
//抽象类中可以没有抽象方法,但包含了抽象方法的类必须被定义为抽象类
//如果子类没有实现父类的所有抽象方法,子类必须被定义为抽象类
//没有抽象构造方法,也没有抽象静态方法
//抽象类中可以有非抽象的构造方法,创建子类的实例时可能调用
接口
public interfaceMyInterface {public void foo();//其他方法}
1.接口的特性
//接口不可以被实例化
//实现类必须实现接口的所有方法
//实现类可以实现多个接口 implements、多个接口使用逗号隔开
//接口中的变量都是静态常量(public static final)
2.面向接口编程
程序设计时:
关心实现类有何能力,而不关心实现细节
面向接口的约定而不考虑接口的具体实现
异常
1.定义:
异常是指在程序的运行过程中所发生的不正常的事件,它会中断正在运行的程序
2.Java的异常处理的5个关键字:try、catch、finally、throw、throws
try() :执行可能产生异常的代码,放到这个模块
catch() 发生异常时,捕获异常,丢给E
finally() 无论是否发生异常,代码总能执行
throw()手动抛出异常
throws()抛出的各种异常声明方法可能要抛出各种异常
printStackTrace()的堆栈跟踪功能显示出程序运行到当前类的执行流程
可以打印出异常堆栈信息
//异常类型 InputMismatchException
java.util.InputMismatchException
//哪一个方法(main)中抛出了异常,出现异常的位置 Test3.java:15
at cn.jbit.exception.Test3.main(Test3.java:15)
getMessage()返回异常信息描述字符串,是printStackTrace()输出信息的一部分
eg:
package com.dx.test04;
import java.util.Scanner;
public class Java01 {
public static void main(String[] args) {
Scanner input = new Scanner(System.in);
int a = input.nextInt();
if (a > 10) {
try {
//1、将所有的可能出现的异常代码放到try
System.out.println("创建流对象"); //出现异常前的都会被执行并输出
System.out.println(10 / 0);
System.out.println("写文件");
} catch (Exception e) { //若 catch (异常类型ex) 异常类型不匹配,程序中断
// 2捕捉异常 ->异常处理(只有出现异常了,才会执行catch)
e.printStackTrace(); //打印出现的异常情况
System.out.println("出现异常啦.....");
return XXX; //如果有return 要先执行finally 再返回catch执行return
} finally {
//不管有异常还是没有异常,finally代码一定会被执行
//唯一不执行的情况,catch没抓到异常 ,直接报错,中断程序了,退出Java虚拟机
System.out.println("释放流");
}
}else{
System.out.println("我也不知道干啥...");
}
System.out.println("不能影响我去玩....");
}
}
打印结果:
创建流对象
出现异常啦.....
释放流
不能影响我去玩....
java.lang.ArithmeticException: / by zero
at com.dx.test04.Java01.main(Java01.java:11)
多重catch块
//引发多种类型的异常
排列catch语句的顺序:
先子类后父类
发生异常时按顺序逐个匹配
只执行第一个与异常类型匹配的catch语句
tips:
//try-catch-finally结构中try语句块是必须的,catch、finally语句块均可选,但两者至少出现之一
//try-catch块中存在return语句,是否还执行finally块? 如果执行,说出执行顺序
//try-catch-finally块中,finally块唯一不执行的情况是什么?
声明异常
throw 自动抛出异常
public void myMethod() throw IOException, SQLException {
// 方法体
}
throws 手动抛出异常
public void myMethod() throws IOException, SQLException {
// 方法体
}
如果在一个方法体中抛出了异常,如何通知调用者?
throws声明某个方法可能抛出的各种异常,多个异常用逗号隔开
//方式1:调用者处理异常
//方式2:调用者继续声明异常 ⚫main()方法声明的异常由Java虚拟机处理
throw与throws区别
//如果一个值为null,不能.属性和方法,一旦.就抛出空指针异常