OOP——核心

面向对象三大特性

构造器引入

  //类中有五大成员,且必需有构造器。
  //若不显示声明任何构造器,则会系统默认提供空参构造器。
  //若显示声明构造器,则系统不提供构造器。

  //提供默认构造器可以通过javap命令反编译字节码文件,从而查看系统提供的空参构造器
  class Person {
      String name;
      int age;
      public void eat() {
          System.out.println("干饭");
      }
  }
// 该类生成的字节码文件通过javap命令反编译后的结果,见下图

OOP——核心

  //构造器的用法(显示声明)
  class Person {
      String name;
      int age;
      
      public Person() {
        //空参构造器
      }

      //一旦声明构造器(无论有无参数),系统都将不再提供默认的空参构造器 ---仍然可用javap反编译查看
      public Person(String name, int age) {
        //带参数的构造器,一般用于初始化属性
        this.name = name;
        this.age = age;
      }
      
      public void eat() {
          System.out.println("干饭");
      }
  }

1.封装

是一种思想,一种开发经验,私有化某些成员,通过提供公共的方法去访问或修改

//未封装
class Person {
  String name;
  int age;
}

Person p = new Person();
//可以直接访问属性,并修改
p.name = "张三";
System.out.println(p.name);
//封装(私有化属性,类外无法直接访问,提供公共的getXxx()和setXxx()方法去访问或修改)
class Person {
  String name;
  int age;

  public String getName() {
    return name;
  }
  public void setName(String name) {
    this.name = name;
  }

  //属性age的get/set方法同上
}

Person p = new Person();

//p.name = "张三"; //不可直接访问或修改属性

p.setName("薛定猫的谔");
System.out.println(p.getName());

2.继承

问题引入:以下代码太过冗余,重复性高,代码健壮性不好,更不利于管理
class Person() {
  String name;
  int age;
  int tall;
    
  public void eat() {
     System.out.println("人吃饭");
  } 
  public void work() {
     System.out.println("人要工作");
  }
}
//***************************************
class Student() {
  String name;
  int age;
  int tall;
  double score; //学生有成绩
  int id; //学生有学号

  public void eat() {
     System.out.println("人吃饭");
  }    
  public void work() {
     System.out.println("学生学习");
  }
}
//***************************************
class Teacher() {
  String name;
  int age;
  int tall;
  double salary; //老师有工资
    
  public void eat() {
     System.out.println("人吃饭");
  } 
  public void work() {
     System.out.println("老师教学");
  }
}


技术引入:继承 关键字(extends)
class A extends B {
  //正常编写A类所特有成员
}
//A直接获取所有B中所有的成员(除构造器外)


class Person() {
  String name;
  int age;
  int tall;
    
  public void eat() {
     System.out.println("人吃饭");
  } 
  public void work() {
     System.out.println("人要工作");
  }
}
//***************************************
class Student() {
  double score; //学生有成绩
  int id; //学生有学号

  public void work() {
     System.out.println("学生学习");//对父类的方法重写
  }
}
//***************************************
class Teacher() {
  double salary; //老师有工资
  
  public void work() {
     System.out.println("老师教学");
  }
}
继承的本质:建立类之间的查找关系(类加载时构建),默认从子类本身开始查找要访问的成员
           1.查找(一旦查找到,不在查找) 2.访问权限(允许访问,访问成功,否则报错)

方法区:加载类信息(属性 方法)
       访问方法时,从方法区加载类信息开始查找(默认从自身类信息开始访问)
堆:堆中创建对象时会创建多组属性,一组自身继承父类的属性,一组原本父类的属性

OOP——核心

继承的核心:
1.继承的本质:建立类之间的查找关系(见上面内存图)
2.查找:就近查找(默认从子类开始 或 super.成员(从直接父类开始查询,super不能多级使用(super.super.成员)))

3.多态

OOP——核心

问题引入
  //需要继承Animal成为具体的动物并创建对象,继承Food成为具体的食物并创建对象,然后两个对象作为参数传递给下面方法
  public void feed(Animal animal, Food food) { //简写(人"类"的喂食feed方法)
    System.out.println("主人给" + animal.getName() + " 吃 " + food.getName()); 
  }
多态技术引入
   Person p = new Person();
    
   Animal animal = new Cat();
   Food food = new Fish();
   p.feed(Animal animal, Food food)
   
   animal = new Dog();
   food = new bone();
   p.p.feed(Animal animal, Food food)
多态的前提是封装和继承---重写、等
class Animal {
  String name;
  int age;
  
  public void eat() {
    System.out.println("进食");
  }
}

Class Cat extends Animal{
  //特有属性
  Sring color = "薛定谔的猫";
  
  public void eat() {
    System.out.println("进食"); 
  }
  
  //特有方法
  public void cry() { 
    System.out.println("进食");
  }
}
//********************************

//java是先通过JDK中的工具 javac.exe编译源文件---> .class文件 ---> 工具java.exe运行程序解释执行
// 先编译 ---> 再运行
Animal cat = new Cat(); // 默认向上转型(自动) ---父类引用指向子类对象
  animal 的编译类型是Animal
  animal 的运行类型是Cat ----实际指向堆内存中的对象是Cat类的对象
  结果就是:父类对象——>子类对象
    1.访问成员编译器只认编译类型即父类中声明的所有成员
    2.而实际真正访问的对象则是时子类中同名的成员(若是方法,则可能被子类重写)---就近查找,动态绑定
向下转型:由于编译类型决定了能访问的成员,所以如果想要访问子类特有的成员
         让子类引用指向子类对象
         Cat cat = (Cat) animal; //相当于 父类引用--->子类对象 ===> 子类引用--->子类对象
         
         前提是animal运行类型(即所指向的对象)是Cat类型的对象 + if(animal instanceOf Cat) {Cat cat = (Cat) animal;}
         现在是 Cat类型的引用---->Cat的对象 
         完全可以访问Cat对象的所有成员

// A instanceOf B; 对象A是否是这个类B或者是它的子类的一个实例(运行类型,一定是对象)
核心:
1.编译类型 和 运行类型(getClass()方法获取)
2.动态绑定---> 动态绑定体现了Java的继承与多态,在继承链中,JVM一直沿着继承链动态找到带有该方法的实现
3.对属性而言,运行时哪个对象调用属性,这个属性就是当前对象的属性,没有则沿继承链查找

OOP——核心

核心两句

  1.继承的本质是建立类之间的查找关系
  2.分清编译类型和运行类型,就近查找 + 动态绑定

OOP——核心

上一篇:取gridview中textbox的值【C#】


下一篇:WinZip Pro 9 for mac(压缩解压工具) v9.0.5520注册版