完整的Java面向对象笔记

提示:面向对象笔记


前言

提示:花了一个星期整理的java笔记


提示:以下是本篇文章正文内容,下面案例可供参考

对象和类

区别

  • 面向过程编程:一堆方法,调来调去
  • 面向对象编程:是以对象未核心,围绕着对象做操作
  • 面向接口编程:面向对象的基础,抽接口
  • 面向对象的优点:复用性好,可维护性好、可扩展性好、移植性好
  • 面向过程:实在
  • 面向对象:抽象

难点

  1. 学完面向对象晕是正常的--------多练、多想
  2. 不晕两种情况:1、什么都不懂 2、以为自己不晕—语法掌握
  3. 6天:掌握语法,知道何时用
  4. 完成打飞机小游戏—面向对象6天内容实际的应用

面向过程的缺点

  1. 缺乏对象数据的封装
  2. 数据和方法是分离状态
package com.lagu.homwork2.com.danei.review.taks1;

public class mianxiangguocheng1 {
    public static void print(String name,int age,char gender,double salary){
        System.out.println("姓名:" + name);
        System.out.println("年龄:" + age);
        System.out.println("性别:" + gender);
        System.out.println("工资:" + salary);
    }

    public static void main(String[] args) {
        String name = "张三";
        int age = 25;
        char gender = '男';
        double sal = 5000;
        print(name,age,gender,sal);

        System.out.println("----------------------");

        String a = "abc";
        int b = -1000;
        char c = '国';
        double  d = -1000;
        print(a,b,c,d);

    }
}

//四个原元素谁都可以调用,且相互独立
  • 而面向对象 可以使用抽象数据类型来解决

抽象数据类型

抽象数据类型可以理解为:将不同类型的数据的集合组成一个整体用来描述一种新的事物

将name,age,gender,salary— 包到一种类型中
在这里插入图片描述

什么是类1

  • 类定义了一种抽象数据类型
  • 类不但定义了抽象数据类型的组成(成员变量),同时还定义了可以对该类型实施的操作(方法)。

例如:

/**
 * 定义雇员类
 */
public class Emp {
    String name;
    int age;
    char gender;
    double salary;

    public static void printEmp(Emp emp){
        System.out.println("姓名:" + emp.name);
        System.out.println("年龄:" + emp.age);
        System.out.println("性别:" + emp.gender);
        System.out.println("工资:" + emp.salary);
    }

    public static void main(String[] args) {
        //使用new 关键字创建Emp类型的对象
        Emp emp1 = new Emp();  // emp1 可以看成对象(实际上是引用)
        //为该对象的各个成员变量赋值
        emp1.name = "abc";
        emp1.age = 25;
        //使用该对象调用
        printEmp(emp1);
        emp1.salary = 15000;
        printEmp(emp1);
    }
}

什么是类2

  • 定义了Emp类以后,提升了代码的模块化以及代码的重用性,但程序依然存在问题:打印信息的方法只能针对Emp数据操作,属于Emp自身的方法,需要实现数据和方法(对该类数的操作)的统一。

改进3.0

/**
 * 定义雇员类
 */
public class Emp {
    String name;
    int age;
    char gender;
    double salary;

    //打印员工信息的方法定义在类中,知道对象成员变量进行操作
    public void printEmp(){
        System.out.println("姓名:" + name);
        System.out.println("年龄:" + age);
        System.out.println("性别:" + gender);
        System.out.println("工资:" + salary);
    }

    public static void main(String[] args) {
        //使用new 关键字创建Emp类型的对象
        Emp emp1 = new Emp();  // emp1 可以看成对象(实际上是引用)
        //为该对象的各个成员变量赋值
        emp1.name = "abc";
        emp1.age = 25;
        emp1.printEmp();
        emp1.salary = 1;
        emp1.printEmp();
    }
}

小结

  1. 现实世界是由很多对象(真实存在的事物:人、笔记本)组成的
  2. 现实世界是现有对象,( 根据共同特征)再抽出类 。
    代码中是先创建类再创建对象
对象
月饼月饼模子
图纸高楼
/**
*学生管理系统
对象:学生、老师、课程
抽出类:学生类、老师类、课程类
*/
class Student{ //学生类
}
class Teacher{//老师类
}
class Cla{//课程类
}
  • 创建对象的语法:类名 对象名 = new 类名();
Scanner sc = new Scanner(System.in);
Random rand = new Random();
  • 一个类可以创建多个对象 。同一个类的多个对象,结构相同,数据不同。
  • 类是一种数据类型
    只能包含:
    1)对象所共有的特征:
    属性------静的
    2)对象所共有的特征:
    行为------动的
    在这里插入图片描述

什么是类3

  • 类是一个**概念(名词)**抽象的定义。简单说就是分类。
  • 类定义了该类型的数据结构,称之为“成员变量”,同时,也定义了一些可以被调用的功能,称之为“方法”。
  • 类是用于构建对象的模板,对象的实质就是内存中一块存储区域,其数据结构由定义它的类来决定。
class Point{
   int x;
   int y;
}

在这里插入图片描述

类的定义——成员变量

  • java语言中,类的成员变量的定义可以使用如下语法:
class 类名{
   成员变量类型 变量名称;
   ...
}

成员变量的初始化

  • 对象创建后,其成员变量可以按照默认的方式初始化;对象成员变量的默认初始化值规则如下表

在这里插入图片描述

定义类的方法

  • 类中除了定义成员变量,还可以定义方法,用于描述对象的行为,封装对象的功能。
  • java语言中,可以按照一下方式定义类中的方法:
class 类名{
      修饰词 返回值类型 方法名词([参数列表]){
          方法体...
      }
      ...
}

使用new关键字创建对象

  • 类定义完成后,可以使用new关键字创建对象。创建对象的过程通常称为实例化。
  • new 运算的语法为:
  new 类名()

类如 new JFrame()可以创建一个窗体对象。

引用类型

  • 除了8钟基本类型外,用类名(接口、数组)声明的变量称为引用类型变量,简称“引用”。
  • 引用类型变量钟存储的是某个对象在内存中的地址信息。引用的功能在于访问对象。引用类型变量按照如下方声明:
  • 引用是对象的代词
    凡是new出来的都是引用类型
类名 引用类型变量名
Point p = new Point();
p.x = 1;
p.x();

在这里插入图片描述

引用类型和基本类型的内存分布

在这里插入图片描述

基本类型和引用类型的区别

  • 引用类型都是 new 出来的 基本类型是可以之间赋值
  • 引用 装的是地址,基本装的是确切的值
  • 引用画等号 ---------指向同一个对象 基本画等号 ---- 赋值

在这里插入图片描述
在这里插入图片描述

  • 基本类型的之间画等号------------在于赋值
    --------身份复印件
  • 引用类型之间画等号---------------在于指向同一个对象
    ----------房子钥匙
    房子:对象
    钥匙:引用
    复杂/配置了一把钥匙给他

举例

/**
 *步骤:
 * 1.找对象----许多格子
 * 2.抽类----class cell{}
 * 3.设计类:
 *   1)成员变量- row 行号 col 列号
 *   2)方法
 */

public class ELuoSi3 {
   int row;
   int clo;

   void printCell() {
        for (int i = 0; i < 20; i++) {
            for (int j = 0; j < 10; j++) {
                if (15 == i &&  6==j){
                    System.out.print("*" + " ");
                }else {
                    System.out.print("-" + " ");
                }
            }
            System.out.println();
        }
    }

    void drop(){ //下落一个格子
       row ++;
    }

    void moveLeft(int n){//左移clo个各种
       clo -= n;
    }

    String getCellInfo(){  //获取格子的坐标
       return row + " " + clo;
    }


    public static void main(String[] args) {
        ELuoSi3 e = new ELuoSi3();
        e.clo = 4;
        e.row = 5;
        e.drop();
        e.moveLeft(2);
        String s = e.getCellInfo();
        System.out.println(s);

        ELuoSi3 cc = new ELuoSi3();
        String ss = cc.getCellInfo();
        System.out.println(ss);
    }
}

  • 运行结构
开始:
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - * - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
下落后:
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - * - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
左移后:
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - * - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
 - - - - - - - - - - 
6 2
  • 代码改进:
  • //把打印方法里不合理,因为:打印背景墙不是格子的行为。
public class cell5 {
   public int row ;
  public  int col ;

    void drop(){
        row++;
    }

    void moveLeft(int n){
        col -= n;
    }

    String  get(){
        return row +",,,"+col;
    }
}

-----------------------------------------------------------------
public class Cell5Test {
    //没有把打印放在Cell5方法里是 是因为:打印背景墙不是格子的行为,放在里面不合理
   public static void printCell1(cell5 c) {  //cell5 c = new cell5();
       for (int i = 0; i < 20; i++) {
           for (int j = 0; j < 10; j++) {
               if (c.row == i && c.col == j) {
                   System.out.print("*" + " ");
               } else {
                   System.out.print("-" + " ");
               }
           }
           System.out.println();
       }
   }
    public static void main(String[] args) {
        cell5 cc  = new cell5();
        cc.col = 5;
        cc.row = 5;
        printCell1(cc);
        cc.drop();
        printCell1(cc);
        cc.moveLeft(3);
        printCell1(cc);

    }
}


null

在这里插入图片描述
在这里插入图片描述

小结

  1. new后,成员变量有默认值
  2. 创建对象语法 :
    类名 引用 = new 类名();
    其中 new 类名() 是在创建对象
    因为对象为数据,所以声明引用来指代数据
  3. 访问成员变量、访问方法
    ----通过点来操作,语法:
    引用.成员变量
    引用.方法名();
  4. 基本类型值之间画等号 ------ 在赋值
    ----身份证复印件
    引用类型之间画等号------指向同一个对象
    ----房子钥匙
  5. null:空,没有指向对象
    若引用的值为null,则不能再进行 . 操作
    否则会出现 NullPointException异常(空指针异常)

return

  • 终结方法 和返回一个值
  • return;只是用来终结方法 和停止方法的执行

方法的重载

JVM内存结构

方法区

在这里插入图片描述

在这里插入图片描述

在这里插入图片描述

方法签名

  • java规定方法签名必须不一样

在这里插入图片描述
在这里插入图片描述

  • 参数列表不同指的是:顺序、个数、类型不同

在这里插入图片描述

编译时会根据签名调用不同的方法

在这里插入图片描述

重载的好处

  • 让用户调用方法更方便
  • java建议: 1个文件只包含1个类型
  • java规定:java一个文件中可以包含多个类,但是public 的类只能有一个
  • public 修饰的类 必须和文件名相同

举例

  • 方法重载
package com.lagu.homwork2.com.danei.review.taks1;

public class cell5 {
   public int row ;
  public  int col ;

    void drop(){ //下落一格
        row++;
    }
    void drop(int n){ //下落n格
        row += n;
    }
    void moveLeft(){//左移一格
        col--;
    }
    void moveLeft(int n){//左移n格
        col -= n;
    }
    void moveRight(){//右移一格
        col++;
    }
    void moveRight(int n){//右移n格
        col += n;
    }
    String  get(){//返回前 行 和 列
        return row +",,,"+col;
    }

}

小结

  1. 方法签名: 方法名+参数列表
  2. 方法的重载:在一个类中方法名相同,参数列表不同
  3. 编译器 在编译时根据签名绑定不同方法

构造方法

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

  • 在没有构造方法前
package com.lagu.homwork2.com.danei.review.taks1;

import com.lagou.task10.Student;

public class Student6 {
    String name;
    int age;
    String address;
    void study(){}
    void sayHi(){
        System.out.println(name + " ," + age + " ," + address);
    }
    void setInfo (String name1,int age1,String address1){//给成员变量赋值
       name =  name1;
       age = age1;
       address = address1;
    }
}
class StudentTest{

    public static void main(String[] args) {
        Student6 zs = new Student6();
        zs.name = "zhangsan";
        zs.age = 25;
        zs.address = "河北";
        zs.sayHi();

        Student6 ls = new Student6();
        ls.setInfo("lisi",26,"吉林");
        ls.sayHi();
    }
}

运行结果:

zhangsan ,25 ,河北
lisi ,26 ,吉林

Process finished with exit code 0
  1. 作用:常常用于给成员变量初始化
  2. 与类同名,没有返回值类型
  3. 构造方法是在创建对象时被自动调用
  4. 若自己不写构造方法,编译器给个默认的无参构造,若自己写了,则不再提供无参构造
  5. 构造方可以重载

举例:

import com.lagou.task10.Student;

public class Student6 {
    String name;
    int age;
    String address;
    void study(){}
    void sayHi(){
        System.out.println(name + " ," + age + " ," + address);
    }
    Student6(){ //无参构造方法
    }
    Student6(String name1,int age1,String address1){ //有参构造方法
        name =  name1;
        age = age1;
        address = address1;
    }

}
class StudentTest{

    public static void main(String[] args) {
        Student6 zs = new Student6();
        zs.sayHi();

        Student6 ls = new Student6("lisi",26,"东北");
        ls.sayHi();
    }
}

运行结果:

null ,0 ,null
lisi ,26 ,东北

分析:

Student6 zs = new Student6(); 
//1.创建了一个对象
//2.调用无参的构造方法
  • 若自己不写构造方法,编译器给个默认的无参构造,若自己写了,则不再提供无参构造
import com.lagou.task10.Student;

public class Student6 {
    String name;
    int age;
    String address;
    void study(){}
    void sayHi(){
        System.out.println(name + " ," + age + " ," + address);
    }
    /*Student6(){ //无参构造方法
    }*/
    Student6(String name1,int age1,String address1){ //有参构造方法
        name =  name1;
        age = age1;
        address = address1;
    }

}
class StudentTest{

    public static void main(String[] args) {
        Student6 zs = new Student6();
        zs.sayHi();

        Student6 ls = new Student6("lisi",26,"东北");
        ls.sayHi();
    }
}

运行结果:

Error:(25, 23) java: 无法将类 com.lagu.homwork2.com.danei.review.taks1.Student6中的构造器 Student6应用到给定类型;
  需要: java.lang.String,int,java.lang.String
  找到: 没有参数
  原因: 实际参数列表和形式参数列表长度不同

this关键字

在这里插入图片描述

  1. this指代当前对象,随调指的就是谁
public class Student6 {
    String name;
    int age;
    String address;
    void study(){}
    void sayHi(){
        System.out.println(name + " ," + age + " ," + address);
    }
    Student6(){ //无参构造方法
    }
    Student6(String name,int age,String address){ //有参构造方法
        this.name =  name;  
        this.age = age;     
        this.address = address;
    }

}
class StudentTest{

    public static void main(String[] args) {
        Student6 zs = new Student6();
        zs.sayHi();

        Student6 ls = new Student6("lisi",26,"东北");
        ls.sayHi();
        /*
        ls.name = "lisi";
        ls.age = 26;
        ls.address = "东北";
        */
    }
}
  1. 当名字不冲突时,可以省略this
  2. 用法: this.成员变量----------访问成员变量
    this.成员方法----------访问普通方法
    this()---------------------调构造方法
    void drop(){ //下落一格
        row++;
        //this.row ++ //c.row++
    }

就近原则

public class cell5 {
   public int row;
   public int col;
   cell5(){}
   cell5(int row,int col){ //就近原则
       row = row;
       col = col;
   }
}
  • 加上this 关键字
public class cell5 {
   public int row;
   public int col;
   cell5(){}
   cell5(int row,int col){
       this.row = row;
       this.col = col;
   }
}
public class Student6 {
    String name;
    int age;
    String address;
    void study(){}
    void sayHi(){
        System.out.println(name + " ," + age + " ," + address);
    }
    Student6(){ //无参构造方法
    }
    Student6(String name,int age,String address){ //有参构造方法
        this.name =  name;
        this.age = age;
        this.address = address;
        //this.name ------指的是成员变量
        //name------------指的是局部变量/参数
    }

}

引用类型数组

  • 数组: [ ] 前只要是一个类型就可以
  • 引用类型的定义
//声明int类型数组,名为arr,包含4个元素 
ar 中每个元素都是int 类型
int  [] arr = new int[4]-----基本类型数组

//声明cell型数组,名为arr,包含4个元素
arr 中的每个元素都是cell类型
Cell [] arr = new Cell[4] -----引用类型数组

int是数据类型
cell也是数据类型

Student[] stus = new Student[100];
Random[] rs = new Random[4];
Scanner[] ss = new Scanner[8];

Hero hero = new Hero(); //一个英雄机
//好多子弹 数组
  • 引用类型的3种初始化
new之后,arr中每个元素都是0
int[] arr = new int[4];

new之后,cs 中每个元素都是null
cell[] cs = new Cell[4]; //new 在创建数组
cs[0] = new Cell(); //new在创建对象
cs[1] = new Cell(2);
...

 Cell[] cs1 = {
 new Cell(),
 new Cell(),
 new Cell(3,4),
 new Cell(2,7)
 };
  Cell[] cs1 = new Cell[]{
 new Cell(),
 new Cell(),
 new Cell(3,4),
 new Cell(2,7)
 };
  • 因为只要 [ ] 前是数据类型就可以
  • 数组也是一种数据类型
int [] arr = new int[4];
Cell [] cs = new Cell[4];
声明int[] 类型的数组,名为as,包含4个元素
每个元素,默认值为null
as[0]默认值为null
as[0]int[] 类型
int[] [] as= new int[4] [];
as[0] = new int[2];
as[0] = new int[4];
as[2] = new int[2];
as[3] = new int[5];

给as中第2个元素的第3个元素赋值为100
as[1][2] = 100;
public class Arras {
    public static void main(String[] args) {
        int [][] as = new int[4][];
        System.out.println(as[0][0]); //空指针异常
        //因为 as[0]是int[]类型默认值是null, null.[0] null的.操作会出现指针异常
    }
}

运行结果:

Exception in thread "main" java.lang.NullPointerException

改正:

public class Arras {
    public static void main(String[] args) {
        int [][] as = new int[4][];
        as[0] = new int[2];
        System.out.println(as[0][0]); //空指针异常

    }
}

运行结果:

0
int [][] as = new int[3][];
as[0] = new int[4];
as[1] = new int[4];
as[2] = new int[4];
as[3] = new int[4];
简写:
int [][] as = new int[3][4];
as[0][0] = 100;
as[0][1] = 100;
as[0][2] = 100;
as[0][3] = 100;
as[1][0] = 100;
as[1][1] = 100;
as[1][2] = 100;
as[1][3] = 100;

结论

在这里插入图片描述

  • 引用类型数组的声明

在这里插入图片描述

  • 引用类型数组的初始化
    在这里插入图片描述
    在这里插入图片描述
  • 数组的类型是基本类型数组
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

把数组写活-arr[i].length

public class Arras {
    public static void main(String[] args) {
        int [][] as = new int[4][];
        as[0] = new int[2];
        as[1] = new int[3];
        as[2] = new int[1];
        as[3] = new int[5];
        for(int i=0;i<as.length;i++){
            for(int j=0;j<as[i].length;j++){
                System.out.print(as[i][j]);
            }
            System.out.println();
        }

    }
}

运行结果:

00
000
0
00000

Process finished with exit code 0

小结

  1. 数组是引用类型,数组对象存在堆中
  2. 数组类型可以是基本类型数组 也可以是引用类型数组
  3. 引用类型数组 new 之后每一个类型数组默认初始值为null

练习:

package com.lagu.homwork2.com.danei.review.taks1;

public class Cell {
    int row;
    int col;
    Cell(){}
    Cell(int row,int col){
        this.row = row;
        this.col = col;
    }
    void drop(){ //下落一行
        row++;
    }
    void moveLeft(){ //左移
        col--;
    }
    void moveRight(){ //右移
        col++;
    }
    String PrintInfo(){ //打印行和列
        return row +" ," + col;
    }

    static class T{
        Cell [] cc;
        T(int row,int col){
            cc = new Cell[4];
            cc[0] = new Cell(row,col);
            cc[1] = new Cell(row,col+1);
            cc[2] = new Cell(row,col+2);
            cc[3] = new Cell(row+1,col+1);
        }

        void drop(){ //下落一格
            //cc[0].row++;
            for(int i=0;i<cc.length;i++){
                cc[i].row++;
            }
        }
        void moveLeft(){ //左移一格
            for(int i=0;i<cc.length;i++){
                cc[i].col--;
            }
        }
        void moveRight(){
            for(int i=0;i<cc.length;i++){
                cc[i].col++;
            }
        }
        void print(){
            for(int i=0;i<cc.length;i++){
                System.out.println(cc[i].PrintInfo());
            }
        }
    }

    void printCell(Cell c1){
        for(int i=0;i<20;i++){
            for(int j=0;j<10;j++){
                if(i == c1.row && j==c1.col){
                    System.out.print("*"+ "  ");
                }
                else {
                    System.out.print("-" + "  ");
                }
            }
            System.out.println();
        }
    }
    

    public static void main(String[] args) {

        //T t = new T(1,1);
        Cell c2 = new Cell(4,5);
        //c2.printCell(c2);
        c2.PrintInfo();

        T c3 = new T(1,2);
        c3.print();
        c3.drop();
        System.out.println("下落");
        c3.print();

    }

}

运行结果:

"C:\Program Files\Java\jdk-11.0.8\bin\java.exe" "-javaagent:D:\Program Files\JetBrains\IntelliJ IDEA 2019.3.3\lib\idea_rt.jar=60285:D:\Program Files\JetBrains\IntelliJ IDEA 2019.3.3\bin" -Dfile.encoding=UTF-8 -classpath C:\Users\dlz\Desktop\java\out\production\javase com.lagu.homwork2.com.danei.review.taks1.Cell
5 ,5
----------
原始
1 ,2
1 ,3
1 ,4
2 ,3
下落
2 ,2
2 ,3
2 ,4
3 ,3

Process finished with exit code 0

对象内存管理

  • 对象内存管理

在这里插入图片描述

堆内存

在这里插入图片描述

成员变量的声明周期

在这里插入图片描述

  • 垃圾回收机制

在这里插入图片描述

java内存泄漏问题

  • 回收没有被引用指向的对象
    在这里插入图片描述
  • system.gc()方法
    在这里插入图片描述

小结

  • 堆中装的是 new出来的对象、数组(包括成员变量)
  • 成员变量生命周期,创建对象时存在,对象被回收时消失
  • 垃圾回收器(gc)不定时回收没有引用指向的对象,回收过程透明,想快些调用System.gc() 方法
  • 内存泄漏:不再使用的对象未被及时回收 ,建议对象不用,引用为null

栈区

  • 栈区用于存放方法中的局部变量
    在这里插入图片描述
  • 局部变量的声明周期

在这里插入图片描述在这里插入图片描述

成员变量和局部变量区别

- List item

小结

  1. 栈用于存储所有局部变量
  2. 调用方法时,栈中分配改方法的栈帧 。栈帧中包括 参数及(方法的)局部变量。方法执行结束,栈帧被清除,局部变量失效。

方法区

  • 方法区用于存放类的信息

  • 程序编译后 产生 类.class字节码文件,被存放在方法区

在这里插入图片描述
在这里插入图片描述

  • 方法只有一份
    在这里插入图片描述

小结

  1. 方法区:存储 类的信息— .class 及方法
  2. 方法只有1份,通过 this 区分对象

继承

  • 继承:避免重复的代码
    父类中包含所有子类公有的数据
    子类中包含子类所特有的数据

  • 泛化的过程
    把公共的抽出父类
    在这里插入图片描述

extends关键字

  • 继承具有传递性
    在这里插入图片描述

this() 调用构造方法

package com.lagu.homwork2.com.danei.review.task3;

public class TetorminorTest {
    public static void main(String[] args) {
     T t = new T();
     t.drop();
     t.print();
     printCell(t);
     O oo = new O(5,5);
        oo.print();
        printCell(oo);
    }

    public static void printCell(T t){  // 放在测试类合适:不属于父类和子类的行为
        for (int i=0;i<20;i++){
            for(int j=0;j<10;j++){
                boolean flag = true; //默认打 -
                for(int k=0;k<4;k++) {
                    if (i == t.cells[k].row && j == t.cells[k].col) {
                        flag = false;
                        System.out.print("* ");
                        break;
                    }
                }
                if(flag){
                    System.out.print("- ");
                }
            }
            System.out.println();
        }
    }
    public static void printCell(O t){  // 放在测试类合适:不属于父类和子类的行为
        for (int i=0;i<20;i++){
            for(int j=0;j<10;j++){
                boolean flag = true; //默认打 -
                for(int k=0;k<4;k++) {
                    if (i == t.cells[k].row && j == t.cells[k].col) {
                        flag = false;
                        System.out.print("* ");
                        break;
                    }
                }
                if(flag){
                    System.out.print("- ");
                }
            }
            System.out.println();
        }
    }
}

class  Tetorminor {
    cell[] cells;
    Tetorminor(){
       cells = new cell[4];
    }
    void drop() {
        for (int i = 0; i < cells.length; i++) {
            cells[i].row++;
        }
    }

    void moveLeft() {
        for (int i = 0; i < cells.length; i++) {
            cells[i].col--;
        }
    }

    void moveRight() {
        for (int i = 0; i < cells.length; i++) {
            cells[i].row++;
        }
    }

    void print() {
        for (int i = 0; i < cells.length; i++) {
            System.out.println(cells[i].printInfo());
        }
    }
}
class T extends Tetorminor {
        T(){this(0,0); }
        T(int col,int row){
            super();
            cells = new cell[4];
            cells[0] = new cell(row,col);
            cells[1] = new cell(row,col+1);
            cells[2] = new cell(row,col+2);
            cells[3] = new cell(row+1,col+1);
        }

    }
    class O extends Tetorminor{
        O(){this(0,0);}
        O(int col,int row){
            cells = new cell[4];
            cells[0] = new cell(row,col);
            cells[1] = new cell(row,col+1);
            cells[2] = new cell(row+1,col);
            cells[3] = new cell(row+1,col+1);
        }
    }



  • 运行结果
1,0
1,1
1,2
2,1
- - - - - - - - - - 
* * * - - - - - - - 
- * - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
5,5
5,6
6,5
6,6
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - * * - - - 
- - - - - * * - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 

Process finished with exit code 0

super() 和 this()

  • this(0,0) 是调用本类的构造方法
  • super 自己不写默认添加,调用父类的构造方法,默认调用父类的无参构造
 class T extends Tetorminor {
        T(){this(0,0); }  // 调用本类构造
        T(int col,int row){ 
            super();  //自己不写默认添加
            cells = new cell[4];
            cells[0] = new cell(row,col);
            cells[1] = new cell(row,col+1);
            cells[2] = new cell(row,col+2);
            cells[3] = new cell(row+1,col+1);
        }

    }
  • 先调用父类的构造函数,再调用子类的构造函数
    举例:
public class SuperDemo {
    public static void main(String[] args) {
        Boo bb = new Boo();
    }
}

class Aoo {
    Aoo(){
        System.out.println("父类构造");
    }
}
class Boo extends Aoo{
    Boo(){
        System.out.println("子类构造");
    }
}

运行结果:

父类构造
子类构造
  • super 一定会调用,且要保持和父类的参数一致
  • super一定要放在第一句话
public class SuperDemo {
    public static void main(String[] args) {
        Boo bb = new Boo();
    }
}

class Aoo {
    Aoo(int a){
        System.out.println("父类构造");
    }
}
class Boo extends Aoo{
    Boo(){
        super(5);  //必须位于子类构造的第一句
        System.out.println("子类构造");
    }
}

继承中的构造方法

在这里插入图片描述
在这里插入图片描述

小结

  • 继承:作用:避免代码的重复
  • 通过extends关键字实现继承,子类继承父类后 将具有本类的成员以及父类的成员。
  • java 中一个类只能继承一个父类,但一个父类可以有多个子类
  • java规定构造子类之前必须先构造父类 ,若自己不写super 则在子类构造中默认添加 super(); 来调用父类无参构造。注意super() 必须位于子类构造的第一句。

向上造型

在这里插入图片描述

  • 举例
public class UpTest {
    public static void main(String[] args) {
        // 能点出来什么,看类型
        Moo o = new Noo(); //向上造型
        o.m =5;
        o.say();
        o.n = 5;  // error
        o.show =5; //error
    }
}
class Moo{
    int m;
    void say(){}
}
class Noo extends Moo{
    int n;
    void show(){}
}

父类类型的引用指向子类类型的对象

在这里插入图片描述

  1. 能点出来什么,看类型
    在这里插入图片描述

小结

  1. 向上造型:父类类型的引用 指向子类型的对象
  2. 能点出来什么看类型,和对象无关
  3. 向上造型的意义: 让子类共用一种父类类型

用法举例(参数例子):

package com.lagu.homwork2.com.danei.review.task3;

public class TetorminorTest {
    public static void main(String[] args) {
    Tetorminor t = new T(0,0);   //先造型再传值
    printCell(t);
    Tetorminor o = new O(5,5);   //先造型再传值
    printCell(o);
    T t1 = new T(4,3);
    printCell(t1);  // 传值的同时造型
                  // Tetorminor t = new T
    }
    public static void printCell(Tetorminor t){  // Tetorminor t = new T(); 或者 Tetorminor t = new O();  //面向对象的思想传的是对象而不是数据
        for (int i=0;i<20;i++){
            for(int j=0;j<10;j++){
                boolean flag = true; //默认打 -
                for(int k=0;k<4;k++) {
                    if (i == t.cells[k].row && j == t.cells[k].col) {  //t.cells[] 是对象的数据。而这个数据又是一个对象
                        flag = false;
                        System.out.print("* ");
                        break;
                    }
                }
                if(flag){
                    System.out.print("- ");
                }
            }
            System.out.println();
        }
    }

}

class  Tetorminor {
    cell[] cells;
    Tetorminor(){
       cells = new cell[4];
    }
    void drop() {
        for (int i = 0; i < cells.length; i++) {
            cells[i].row++;
        }
    }

    void moveLeft() {
        for (int i = 0; i < cells.length; i++) {
            cells[i].col--;
        }
    }

    void moveRight() {
        for (int i = 0; i < cells.length; i++) {
            cells[i].row++;
        }
    }

    void print() {
        for (int i = 0; i < cells.length; i++) {
            System.out.println(cells[i].printInfo());
        }
    }
}
class T extends Tetorminor {
        T(){this(0,0); }
        T(int col,int row){
            super();
            cells = new cell[4];
            cells[0] = new cell(row,col);
            cells[1] = new cell(row,col+1);
            cells[2] = new cell(row,col+2);
            cells[3] = new cell(row+1,col+1);
        }

    }
    class O extends Tetorminor{
        O(){this(0,0);}
        O(int col,int row){
            cells = new cell[4];
            cells[0] = new cell(row,col);
            cells[1] = new cell(row,col+1);
            cells[2] = new cell(row+1,col);
            cells[3] = new cell(row+1,col+1);
        }
    }


运行结果:

* * * - - - - - - - 
- * - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - * * - - - 
- - - - - * * - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - * * * - - - 
- - - - - * - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 
- - - - - - - - - - 

Process finished with exit code 0

返回值的例子:
在这里插入图片描述在这里插入图片描述

重写

概念

  • 发生在两个类中,并且是子父的关系,子类方法和父类方法签名相同,子类重写了父类方法
  • 当方法被重写时时,掉那个看对象在这里插入图片描述
    在这里插入图片描述
  • 如果在子类重写的方法中父类的方法使用super.show()方法
    在这里插入图片描述
  • 重写(override)和重载(overload)的区别
    重写:在一个类中,方法名相同,参数列表不同
    重载:在两个类中,并且是子类和父类的关系,签名相同。
    在这里插入图片描述
  • 重载:编译时------ .java 到 .class的过程
  • 重载时候看类型(看 obj的类型)
    内存没东西—只看语法对不对
  • 重写:运行时------ jvm加载.class 并运行.class的过程
  • 重写看对象
    内存才有东西

在这里插入图片描述

import com.sun.security.jgss.GSSUtil;

import java.security.spec.RSAOtherPrimeInfo;

public class CxCz {
    public static void main(String[] args) {
        Ao1 ao1 = new Bo1();
        Coo coo = new Coo();
        coo.t(ao1);
    }
}

class Coo {
    void t(Ao1 o){
        System.out.println("333");
        o.show();
    }
    void t(Bo1 o){
        System.out.println("444");
        o.show();
    }
}

class  Ao1 {
    void show(){
        System.out.println("111");
    }
}

class  Bo1 extends  Ao1 {
    void show(){
        System.out.println("222");
    }
}
333
222

Process finished with exit code 0

在这里插入图片描述

小结

  1. 重写: 发生在两个类中,并且是子父类的关系,子类方法和父类方法的签名一样
  2. 重写时可以通过super来访问父类的方法
  3. 重载为编译期绑定,看类型。重写为运行期绑定,看对象

package,import

  1. package 解决类的命名冲突问题
    在这里插入图片描述

  2. 格式:package 包名1.包名2…包名n;
    在这里插入图片描述

  3. 使用import 对类全称进行声明

  4. import java.util.Scanner;

  5. import java.util.Arrays;

  6. import java.util.Random;

  7. import java.util.*;----不建议

  8. 同一个包里的类不需要使用import
    在这里插入图片描述

小结

  1. package 用于避免类的命名冲突,java建议每个类写包名。类的全局限定名 ------------包名 + 类名
  2. import 用于声明类,或者叫引入类。 访问不同包中类时,需要import

访问修饰符public、private

封装的意义

  • 把数据包装起来,保护数据
    在这里插入图片描述
  • 当内部细节改变,只要保证对外定义的功能不变,其它模块就不会受牵连
    在这里插入图片描述
    在这里插入图片描述

private和public

  • private 修饰的成员遍历和方法只能在本类中调用
  • public 修饰的可以在任何地方调用
    在这里插入图片描述

protected 和默认访问控制

  • 默认只能被同包访问
  • protected 可以被同包类和子类访问
    在这里插入图片描述
  • 类的修饰词 只能是public 或者 默认
    在这里插入图片描述
    在这里插入图片描述

小结

  • 访问修饰符 :public 共有的任何类都可以访问
  • protected 受保护的 :本类子类同包类可以访问
  • 默认 ,什么也不写 ,本类同包类
  • private :私有的,只能本类访问
  • 类只能用 public 或默认的
  • 类的成员如上四种都可以
  • 修饰局部变量没有意义

static,final

  • 建议和main 平行的方法 加上 static

static 修饰成员变量

  • static 修饰的变量不属于对象,属于类 通过 类名.来访问
    在这里插入图片描述
  • static 修饰的的在方法区中
class Aoo {
    int a; //属于对象
    static int b; //属于类型  在方法区中
    void show(){}
}

在这里插入图片描述
static 修饰的变量只有一份
在这里插入图片描述
而且被共享
在这里插入图片描述
举例:

public class Static {
    public static void main(String[] args) {
    Aoo a1 = new Aoo();
    a1.show();  //1,1

    Aoo a2 = new Aoo();
    a2.show(); //1 ,2
    }
}
class Aoo {
    int a; //属于对象
    static int b; //属于类型
    Aoo(){
        a++;
        b++;
    }
    void show(){
        System.out.println(a);
        System.out.println(b);
    }
}

结果:

1
1
1
2

Process finished with exit code 0

在这里插入图片描述

成员变量:

1)实例变量------------不用static修饰的
2)静态变量------------static变量

何时用静态变量,何时用实例变量
当所有对象共用这个变量,使用静态变量
在这里插入图片描述

  • 可以 通过 类名. 访问(建议) 且不需要new 对象 和对象没有关系
public class Static {
    public static void main(String[] args) {
  //   Aoo a1 = new Aoo();
  //  a1.show();  //1,1
  //      System.out.println(a1.b);
        System.out.println(Aoo.b); //建议通过类名. 访问
 //   Aoo a2 = new Aoo();
 //   a2.show(); //1 ,2
    }
}
class Aoo {
    int a; //属于对象
    static int b; //属于类型
    Aoo(){
        a++;
        b++;
    }
    void show(){
        System.out.println(a);
        System.out.println(b);
    }
}

static修饰方法

  • 方法加不加 static的区别: static 修饰的方法是没 this.的
    在这里插入图片描述在这里插入图片描述
    在这里插入图片描述

  • Static 只需要对参数有关
    在这里插入图片描述

小结

  1. 非静态方法:----有隐式this
    可以直接访问静态变量和实例变量
    需要访问实例变量

  2. 静态方法:----没有隐式this
    只能直接访问静态变量,不能直接访问实例变量

  3. 何时用静态方法,何时用非静态方法:
    不需要访问实例变量时即可使用

static块

在这里插入图片描述
举例:

public class Static {
    public static void main(String[] args) {
        Coo c1 = new Coo(); // 111
        Coo c2 = new Coo(); // 111
    }
}
class Coo{ //static 块
    Coo(){
        System.out.println("111");
    }
    static { //加载类的时候被执行 ,只执行一次 ,因为类只被加载一次
        System.out.println("静态代码块");
    }
}

结果:

静态代码块
111
111

Process finished with exit code 0

何时使用静态代码块

  • 一般用于加载静态资源(图片、音频、视频)

小结

  1. static修饰成员变量 :属于类 ,不属于对象,存在方法区中,只有一份。为所有对象公有的数据,常常通过类名来访问 。何时用:某个数据被所有对象共享公有
  2. static修饰方法:没有隐式this 传递,不能直接访问实例变量。 何时用:方法的执行只于参数相关,与对象无关。常常通过类名直接访问
  3. static 块:属于类的块,在类加载期间执行,并且只执行一次。 何时用:常用于加载静态资源(图片,音频,视频)

final关键字

final修饰变量

  • 意味着不可变
  • 修饰的成员变量,只能在声明或构造函数中初始化
    在这里插入图片描述
    举例
class Doo{ //final修饰变量
    final int a = 5; //声明同时初始化
    final int b;
    Doo(){
        b = 5;       //先声明,再在构造中初始化
    }
    void show(){
        final int c; //一般都不用
       // System.out.println(c); 错误 c没有(值)初始化
        c = 5;
        System.out.println(c);
    }
    void say(){
        //a = 88; // 错误,final 修饰的错不能改变 
    }
}

final修饰方法

在这里插入图片描述
举例:

class Eoo{ //finl修饰的方法--不可被重写
    void show(){ }
    final void say(){ }

}
class Foo extends Eoo{
    @Override
    void show(){
    }
   // void say(){} //错误,final方法不能被重写
}

举例:

  • 修饰的类不被继承

final修饰类

在这里插入图片描述
举例:

class Ioo{}
final class  Goo extends Ioo{ //可以继承别的类 
}
//class Hoo extends Goo{} //错误,final 修饰的类不能被继承

小结

  1. final修饰变量,只能在声明和构造函数时初始化,变量不能被修改 。
  2. final修饰方法,不可被重写
  3. final 修饰类不可被继承

static final

  • 声明同时必须初始化
    在这里插入图片描述
public class StaticFinal {
    public static void main(String[] args) {
        //编译时,直接将Aoo.PI 替换成3.1415926
        System.out.println(Aoo.PI);
        // 在方法区中加载Aoo.class
        // 以及static 成员,以及方法
        System.out.println(Aoo.num);
    }
}
class  Aoo{
    //声明常量,必须声明的同时初始化
    //建议所有字母大写
    static final  double PI = 3.1415926;
    static int num = 5;
}

小总结

在这里插入图片描述

抽象类、抽象方法

  • 不知道方法体(有多种情况)怎么写,通过子类来写,java不建议空方法,把它写成抽象方法(不完整)
  • 计算相同周长不同形状的面积
    在这里插入图片描述
    在这里插入图片描述
  1. 抽象方法:由abstract修饰
    只有方法的定义,没有方法体的
  2. 抽象类:由abstract修饰
    可以包含抽象方法,也可以包含普通方法
  3. 包含抽象方法的的类,必须是抽象类。类中没有抽象方法,也可以将类声明为抽象类
  4. 抽象类不能被实例化
    shape s = new shape(); //错误
  5. 一般需要被继承:
    1)子类也声明为抽象类
    2)子类重写抽象方法 ----首选
  6. 抽象类的意义:
    1)封装子类公有的成员
    并为子类提供公共的类型
    在这里插入图片描述

2)定义抽象方法,由子类来做不同的实现,但是入口(方法名)是一样的

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

抽象继承类

在这里插入图片描述

抽象类的意义

  • 抽象类也是父类,意义在于避免重复的代码
    在这里插入图片描述
    举例:根据周长计算不同图形的面积
class ShapeDome{
    public static void main(String[] args) {
        //Shape shape = new Shape(); 抽象类不能new 对象
        Shape[] shape = new Shape[2];
        shape[0] = new Yuan(1);
        shape[1] = new Zhen(1);
        max(shape);
    }
    public static void max(Shape[] shape){
        double max = shape[0].area();
        int maxIndex = 0;
        for(int i=0;i<shape.length;i++){
            double area = shape[i].area();
            if(area > max){
                max = area; //重置max的值
                maxIndex = i; //重置最大面积索引
            }
        }
        System.out.println("最大面积:" + max + " 下标是" +maxIndex);
    }

}


abstract public class Shape {
    double c;
    abstract double area();
}

class  Yuan extends Shape{
    Yuan(double c){
        this.c = c;
    }
    @Override
    double area(){
        return 0.796*c*c;
    }
}

class  Zhen extends Shape{
    Zhen(double c){
        this.c = c;
    }
    @Override
    double area(){
        return 0.625*c*c;
    }
}

运行结果

最大面积:0.796 下标是0

小结

  1. 抽象方法:由abstract修饰
    只有方法的定义,没有方法体的
  2. 抽象类:由abstract修饰
    可以包含抽象方法,也可以包含普通方法
  3. 包含抽象方法的的类,必须是抽象类。类中没有抽象方法,也可以将类声明为抽象类
  4. 抽象类不能被实例化
    shape s = new shape(); //错误
  5. 一般需要被继承:
    1)子类也声明为抽象类
    2)子类重写抽象方法 ----首选
  6. 抽象类的意义:
    1)封装子类公有的成员
    并为子类提供公共的类型

接口

  • 接口是一个标准,一个规范,只有满足这个标准才能干某件事。
  • interface 接口名
  • 接口里只能包含常量和抽象方法
  • 接口是抽象的,完全不完整的,不能实例化不能new对象,是制订标准让其它类来实现的
  • 实现接口通过 implements 关键字(实现-遵守标准),而且需要将接口的所有抽象类都实现
  • 一个类可以实现多个接口,用“,”间隔 ,且子类的实现的重写方法的修饰权限必须大于或等于父类的权限
  • 一个类又想继承父类,又想实现接口,必须先继承后实现
  • 接口与接口时间是继承关系

举例:

public interface JieKou {
    public static final  int NUM = 5; //public static final 可以省略
    int B = 5;
    public abstract void show();
    void say();//默认 Public abstract
}
 interface JieKou2{
    void sayHi();
}

class Coo implements JieKou{ //遵守标准
    @Override
   public void show(){
        System.out.println("111");
    }
    @Override
   public void say(){
        System.out.println("222");
    }
}

class  Doo implements JieKou,JieKou2{
    @Override
    public void show(){
        System.out.println("333");
    }
    @Override
    public void say(){
        System.out.println("444");
    }
    public void sayHi(){
        System.out.println("555");
    }
}

class Foo extends Coo implements JieKou,JieKou2{
    public void sayHi(){

    }
}

interface JieKou3 extends JieKou{ //接口之间使用继承
    void sayHello();
}

class Eoo implements JieKou3{ //要重写三个方法
    public void  sayHello(){}
    public void show(){}
    public void say(){}
}

定义一个接口

在这里插入图片描述

实现接口

在这里插入图片描述

  • 接口 可以 . 出来 runner 接口内的东西,子类内地东西 . 不出来
    在这里插入图片描述
  • . 看类型,jiekou 只能. 出来JieKou的内容
  • 重写看对象,继承看类型
class test{
    public static void main(String[] args) {
    JieKou jieKou = new Goo();
    jieKou.say(); //子类的
    jieKou.show(); //子了的
    //jieKou.show1();
    }
}

public interface JieKou {
    public static final  int NUM = 5; //public static final 可以省略
    int B = 5;
    public abstract void show();
    void say();//默认 Public abstract
}

class Goo implements  JieKou{
    void show1(){}
    public  void say(){}
    public void show(){}
}

接口继承

在这里插入图片描述
练习:
在这里插入图片描述

class test{
    public static void main(String[] args) {
    JieKou jieKou = new Goo();
    jieKou.say();
    jieKou.show();
        System.out.println(JieKou.B);
    //jieKou.show1();
    }
}

public interface JieKou {
    public static final  int NUM = 5; //public static final 可以省略
    int B = 5;
    public abstract void show();
    void say();//默认 Public abstract
}

class Goo implements  JieKou{
    void show1(){}
    public  void say(){}
    public void show(){}
}

interface JieKou2{
    void sayHi();
}

class Coo implements JieKou{ //遵守标准
    @Override
   public void show(){
        System.out.println("111");
    }
    @Override
   public void say(){
        System.out.println("222");
    }
}

class  Doo implements JieKou,JieKou2{
    @Override
    public void show(){
        System.out.println("333");
    }
    @Override
    public void say(){
        System.out.println("444");
    }
    public void sayHi(){
        System.out.println("555");
    }
}

class Foo extends Coo implements JieKou,JieKou2{
    public void sayHi(){

    }
}

interface JieKou3 extends JieKou{ //接口之间使用继承
    void sayHello();
}

class Eoo implements JieKou3{ //要重写三个方法
    public void  sayHello(){}
    public void show(){}
    public void say(){}
}

接口和抽象类的区别

  • 抽象类是共有的本质是还是父类,
  • 接口是特别的,不是公有的,只有遵守才能干某事
    在这里插入图片描述
    在这里插入图片描述

在这里插入图片描述
实现类
在这里插入图片描述
. 什么看类型
在这里插入图片描述

多态

  • 多种形态
    在这里插入图片描述
  • 特点1:一个类型的引用指向不同的对象时会有不同的功能
    在这里插入图片描述
    在这里插入图片描述
  • 同一个对象,造型成不同的类型时,会有不同的功能(方法)
    在这里插入图片描述
    在这里插入图片描述

向上造型

在这里插入图片描述

强制类型转换

  • 编译器认为子类大,父类小
  • 强转看对象
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

在这里插入图片描述

instanceof 关键字

在这里插入图片描述

在这里插入图片描述

小结

  1. 同一类型的引用指向不同的对象时 有不同的意义
  2. 同一个对象造型为不同的类型时有不同的功能
  3. 强转:父到子 前提:对象是子 ;转为接口 前提:对象实现了该接口
  4. 强转失败冒异常:通过instanceof来解决
    语法:
    引用 instanceof 数据类型 --------------boolean
    强转成功与否,看对象

举例:

public class DuoTai {
    public static void main(String[] args) {
        /*
         * 向上造型
         */
      /*  JieKou jieKou = new Boo(); //向上造型 是实现类

        Aoo aoo = new Boo();//向上造型  是子类
        aoo.b();// . 看类型
       // JieKou o3 = new Coo(); 错误,类型不匹配 既不是子类 又不是实现类*/

        /**
         * 向上造型时,点出来什么,看类型
         */
        /*Aoo aoo1 = new Boo();//向上造型  是子类
        aoo1.b();// . 看类型
        //aoo1.num1 =5;//编译错误 ,点出来什么看类*/

        //强转看对象
        Aoo o1 = new Boo();//向上造型
        Boo o2 = (Boo) o1;//正确 ,o1指向的对象是Boo所以成功
        JieKou o3 = (JieKou) o1; //正确
                   // o1 指向的对象实现了JieKou
       // Coo o4 = (Coo) o1; //运行报错  ClassCastException 类型转换异常
                           // o1 指向的对象与Coo无关
        
        // instanceof 为true两种情况
        //1.对象为该类型
        //2.对象实现了该接口
        if (o1 instanceof  Coo){ // false
            Coo o4 = (Coo) o1;
        }

    }
}
interface JieKou{
    void a();
}
abstract class Aoo{
    abstract void b();
}
class Boo extends Aoo implements JieKou{
    int num1;
    void b(){}
    public void a(){}
}
class Coo extends Aoo{
    int num2;
    void c(){}
    void b(){}
}
class Doo extends Boo{}

练习:
在这里插入图片描述

public class LianXi {
    public static void main(String[] args) {
        Abs abs = new Eoo();
        abs.b();
        Eoo eoo = (Eoo) abs; //abs的对象为Eoo类型
        eoo.num =5;
        eoo.a();

        Inter inter = (Inter) abs; //abs的对象 实现了 Inter接口

       // Foo foo = (Foo)abs;// abs的对象不是Foo类型

        if(abs instanceof Foo){
            Foo foo1 = (Foo)abs;
        }


    }
}
interface Inter {
    void a();
}
abstract  class  Abs {
    abstract void b();
}
class Eoo extends Abs implements Inter{
    int num;
    void b(){}
    public void a(){}
}
class Foo extends Abs {
    int num2;
    void b(){}
}

应用:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
改动:
在这里插入图片描述
在这里插入图片描述

内部类

  • 类里面套类
  • 一个类只能被另外一个类使用,对外不可见
  • 内部类对象只能在外部类中被创建
    内部类可以直接访问外部类所有成员(包括私有的)

定义成员内部类

在这里插入图片描述
在这里插入图片描述

在这里插入图片描述
##内部类创造对象
在这里插入图片描述

匿名内部类

  • 定义匿名内部类条件:1.只创建一个对象 2. 是子类或者某个接口的实现类
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

在这里插入图片描述

举例:

public interface NiMing {
}
interface NiMing2{
    void show();
}
class test{
    public static void main(String[] args) {
        //创建是实现类对象 名为niMing
        NiMing niMing = new NiMing() {int a;};

       //创建实现类对象 名为niMing2
        NiMing2 niMing2 = new NiMing2() {
            @Override  //实现类的成员
            public void show() { System.out.println("qwer"); }
        };
        niMing2.show();
    }
}

在这里插入图片描述

总结

  1. 面向对象三大特征
    封装:3个层次:类本身就是一种封装,在封装数据、方法 ,把类当成一个整体。方法也是一种封装功能,还要通过访问修饰符来封装。分别实现 :类做为一个整体性强 隐藏实现的细节 保证数据的安全

继承:避免代码重复,使用extends关键字

多态:既多种形态,在继承之上 。
两种实现方法: 一个类型指向不同对象,有不同的实现(一个抽象类的一个方法。被多个子类重写)
同一个对象造型成不同的类型,有不同的功能(一个实现类 实现多个接口)
提高可维护性、可扩展性

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

dlz0836

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

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

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

打赏作者

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

抵扣说明:

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

余额充值