Demo05-面向对象

面向对象

  • 面向对象编程(Object-Oriented Programming,OOP)
  • 面向对象编程的本质就是:以类的方式组织代码,以对象的组织(封装)数据。
  • 抽象
  • 三大特性:
    • 封装
    • 继承
    • 多态

方法的调用

  • 静态方法:
    在这里插入图片描述

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-XrKs6WQL-1645524917063)(C:\Users\Lr\AppData\Roaming\Typora\typora-user-images\image-20220118203634441.png)]

  • 非静态方法:
    在这里插入图片描述

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-EMyoNMfz-1645524917064)(C:\Users\Lr\AppData\Roaming\Typora\typora-user-images\image-20220118205913874.png)]

  • 值传递

    package oop.demo01;
    //值传递
    public class Demo04 {
        public static void  main(String[] args){
            int a = 1;
            System.out.println(a);//1
    
            Demo04.change(a);
    
            System.out.println(a);//1
        }
        //返回值为空
        public static void  change(int a){
            a = 10;
        }
    
    
    }
    

构造器

  • 使用new关键字创建对象

  • 使用new关键字创建的时候,除了分配内存空间之外,还会给创建好的对象,进行默认的初始化以及对类中构造器的调用

  • 类中的构造器也称为构造方法,是在进行创建对象的时候必须调用的。并且构造器有以下两个特点:

    1. 必须和类名字相同

    2. 必须没有返回类型,也不能写void

      作用:

      1. new本质是在调用构造方法

      2. 初始化对象的值

        注意点:

        定义有参构造后,如果想要使用无参构造,显示的定义一个无参的构造

创建对象内存分析

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-SJSyvUr5-1645524917065)(C:\Users\Lr\AppData\Roaming\Typora\typora-user-images\image-20220119111659902.png)]

类与对象

  1. 类与对象

    类是一个模板:抽象,对象是一个具体的实例

  2. 方法: 定义、调用

  3. 对应的引用

    引用类型: 基本类型(8)

    对象是通过引用操作的:栈----->堆

  4. 属性:字段Field 成员变量

    默认初始化:

    数字:0 0.0

    char u0000

    boolean:false

    引用:null

    修饰符 属性类型 属性名 = 属性值

  5. 对象的创建与使用

    必须使用new 关键字创造对象,构造器 Person xiaolizi = new Person();

    对象的属性 xiaolizi.name

    对象的方法 xiaolizi.high()

  6. 类:

    静态的属性 属性

    动态的行为 方法

    封装

    • 高内聚 低耦合 高内聚就是类的内部数据操作细节自己完成,不允许外部干涉,低耦合仅暴露少量的方法给外部使用

    • 封装(数据的隐藏) 通常应禁止直接访问一个对象中数据的实际表示,而应通过操作接口来访问,这称为信息隐藏

    • 属性私有,get/set

      封装的作用
      1. 提高程序的安全性,保护数据

      2. 隐藏代码的实现细节

      3. 统一接口

      4. 系统可维护性增加了

    继承

    1. 继承的本质是对某一批类的抽象

    2. extends 的意思是“扩展”。子类是父类的扩展

    3. JAVA中只有单继承,没有多继承(一个儿子只能有一个爸爸 但是一个爸爸可以有多个儿子)

    4. 继承是类和类之间的一种关系,除此之外,类和类之间的关系还有依赖,组合,聚合等

    5. 继承关系的两个类,一个为子类(派生类),一个为父类(基类)。子类继承父类,使用关键字extends来表示

    6. 在JAVA中,所有的类,都默认直接或者间接继承object
      

super

super注意点:

  1. super调用父类的构造方法,必须在构造方法的第一个

  2. super必须只能出现在子类的方法或者构造方法中

  3. super 和this 不能同时调用构造方法

  4. Student student = new Student();//测试类
    
    public class Student extends Person {  //子类
        public Student() {
            //隐藏代码:调用了父类的无参构造
            System.out.println("Student 无参执行");
        }
        
        public class Person {   //父类
        public Person() {
            System.out.println("Person无参执行");
        }
            
            执行结果:Person无参执行
                    Student 无参执行
    
    

VS this:

代表的对象不同:

this: 本身调用者这个对象

super: 代表父类对象的应用

前提:

this : 没有继承也可以使用

super :只能在继承条件才能使用

构造方法:

this() ; 本类的构造

super(); 父类的构造

重写

重写:需要有继承关系,子类重写父类的方法

  1. 方法名必须相同

  2. 参数列表必须相同

  3. 修饰符:范围可以扩大但不能缩小: public>Protected>Default>private

  4. 抛出的异常:范围,可以被缩小,但不能扩大,ClassNotFoundException—>Exception(大)

    重写(override),子类的方法和父类必须一致,方法体不同

    静态方法:

    public class A extends B{
        public static void test(){
    
        System.out.println("A=>test()");
    }
    }
    
    
    //重写都是方法的重写,和属性无关
    public class B {
    
        public static  void test(){
            System.out.println("B=>test()");
        }
    }
    
    public class Application {
        public static void main(String[] args){
            //方法的调用只和左边,定义的数据类型有关
            A a = new A();
            a.test();//A类的方法
    //父类的引用指向了子类  B类为父类
            B b = new A();
            b.test();//B类的方法
    
    测试结果:
        A=>test()
        B=>test()
    

    非静态方法:

    非静态:重写

/重写都是方法的重写,和属性无关
public class B {

    public   void test(){
        System.out.println("B=>test()");
    }
}


public class A extends B{
   //Override :重写
    @Override //注解:有功能的注释
    public void test() {
        System.out.println("A=>test()");
    }
}

测试结果:A=>test()
        A=>test()

多态

  • 多态:即同一方法可以根据发送对象的不同而采用多种不同的行为方式

  • 一个对象的实际类型是确定的,但可以指向对象的引用的类型有很多。

  • 多态存在的条件

    1. 有继承关系

    2. 子类重写父类方法

    3. 子类引用指向子类对象

    //父类
    public class Person {
        public void run(){
            System.out.println("run");
    
        }
    }
    
    //子类
    public class Student extends Person {
    
        @Override
        public void run() {
           System.out.println("son");
        }
        public void eat() {
            System.out.println("eat");
        }
    }
    
    //测试类
    import oop.demo06.Person;
    import oop.demo06.Student;
    public class Application {
    
        public static void main(String[] args) {
    
            //一个对象的实际类型是确定的
            //new Student();
            //new Person();
    
            //可以指向的引用类型不确定:父类的引用指向子类
    
            //Student 能调用的方法都是自己的或者继承父类的
            Student s1 = new Student();
            //Person父类型,可以指向子类,但是不能调用子类独有的方法
            Person s2 = new Student();
            Object s3 = new Student();
    //对象能执行哪些方法,主要看对象左边的类型,和右边关系不大
            s2.run();//子类重写了父类的方法,执行子类的方法
            ((Student) s2).eat();//可以使用强制类型转换。将大类型转换为小类型
            s1.eat();
        }
    }
    
    测试结果:
        son
        eat
        eat
    
    
  • 多态注意:

    1. 多态是方法的多态,属性没有多态

    2. 父类和子类,有联系 类型转换异常 ClassCastException

    3. 存在条件:继承关系,方法需要重写,父类引用指向子类对象 Father f1 = new Son();

      1. static 方法,属于类,不属于实例

        1. final 常量;
          3. private
          4. 方法;

instanceof (类型转换) 引用类型

public class Application {

    public static void main(String[] args) {
        //Object > String
        //Object > Person > Teacher
        //Object > Person > Student
        Object object = new Student();

        System.out.println(object instanceof Student);//true
        System.out.println(object instanceof Person);//true
        System.out.println(object instanceof Object);//true
        System.out.println(object instanceof Teacher);//False  跟Student 无关是另外的一个分支
        System.out.println(object instanceof String);//False  String 类型是Object下的

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

        Person person = new Student();

        System.out.println(person instanceof Student);//true
        System.out.println(person instanceof Person);//true
        System.out.println(person instanceof Object);//true
        System.out.println(person instanceof Teacher);//False
       // System.out.println(person instanceof String);//编译报错

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

        Student student = new  Student();

        System.out.println(student instanceof Student);//true
        System.out.println(student instanceof Person);//true
        System.out.println(student instanceof Object);//true
        //System.out.println(student instanceof Teacher);//False编译报错
       // System.out.println(student instanceof String);//False编译报错
public class Application {
    public static void main(String[] args) {
        //类型之间的转换
        //子类转换为父类,可能丢失自己本来的一些方法
        Student student = new Student();
        student.go();
        Person person = student;//student(低) ->person(高) 可以自动转换

        Person obj = new Student();
        //student将这个对象转换为Student类型,就可以使用Student类型的方法
        ((Student)obj).go();
    }

注意:

  1. 父类引用指向子类的对象
  2. 把子类转换为父类,向上转型
  3. 把父类转换为子类,向下转型:强制转换
  4. 方便方法的调用,减少重复的代码,简洁

static

  • 非静态的方法可以调用静态方法里的所有东西 而静态方法只能调用静态方法里面的东西 不能调用非静态方法

因为static跟类一起加载

private static int age;//静态变量
private double score;//非静态的变量

public  void run(){

}

public static void go(){

}
public static void main(String[] args){
   go();
  // run();//报错
  • 静态代码块

    public class Person {
        //赋初始值
        {
            System.out.println("匿名代码块");
        }
        //静态代码块只执行一次
        static {
            System.out.println("静态代码块");
        }
            public Person(){
                System.out.println("构造方法");
            }
            public static void main (String[] args){
                Person person = new Person();
            }
    }
    
    测试结果:
        静态代码块
        匿名代码块
        构造方法
        
         public static void main (String[] args){
                Person person1= new Person();
                System.out.println("============");
               Person person2 = new Person();
    }
    
    测试结果:
        
    ============
    匿名代码块
    构造方法
    

注意:用final定义不能实现继承

  • //静态导入包
    import static java.lang.Math.random;
    import static java.lang.Math.PI;
    
    public class Test {
    
        public static void main(String[] args) {
            System.out.println(random());
            System.out.println(PI);
        }
    }
    

抽象类

//abstract 抽象类:类 extends: 单继承(接口可以多继承)
public abstract class Action{
    //约束 可以自行实现
    //abstract,抽象方法,只有方法名字,没有方法的实现!
    public abstract void doSomething();
    
    //1. 不能new 这个抽象类,只能靠子类去实现它;约束
    //2.抽象类中可以写普通的方法1
    //3.抽象方法必须在抽象类中

接口

  • 普通类:只有具体实现
  • 抽象类:具体实现和规范(抽象方法)都有
  • 接口:只有规范 自己无法写方法 约束和实现分离:面向接口编程
  • 声明类的关键字是class,声明接口的关键字是interface
  • 接口不能被实例化,接口中没有构造方法
  • implements 可以实现多个接口
  • 接口中的方法需要重写
/interface 定义的关键字,接口都需要有实现类
public interface UserService {
    //接口中的所有定义都是抽象的 public abstract
    void add(String name);
    void delete(String name);
    void update(String name);
    void query(String name);
}





//抽象类:extends
//类 可以实现接口 implements 接口
//实现了接口的类,就需要重写接口中的方法
public class UserServiceImpl implements  UserService{
    @Override
    public void add(String name) {

    }

    @Override
    public void delete(String name) {

    }

    @Override
    public void update(String name) {

    }

    @Override
    public void query(String name) {

    }
}

//多继承 利用接口实现多继承
public class UserServiceImpl implements  UserService,TimeService {
    @Override
    public void timer() 
        
        
public interface TimeService {
    void timer();
}
    
    
    //常量:public static final 
    //int AGE = 99;


内部类

  • 内部类就是在一个类的内部再定义一个类,比如在A类中定义一个B类,那么B类相对于A类来说就称为内部类,而A类相对B类就是外部类。

    public class Outer {
        private int id = 10;
        public void out(){
            System.out.println("这是外部类的方法");
        }
        class Inner{
            public void in(){
                System.out.println("这是内部类的方法");
            }
    
    1. 成员内部类

      public class Outer {
          private int id = 10;
          public void out(){
              System.out.println("这是外部类的方法");
          }
          class Inner{
              public void in(){
                  System.out.println("这是内部类的方法");
              }
      
              //获得外部类的私有属性  私有方法
              public void getID(){
                  System.out.println(id);
              }
      
          }
      
      }
      public class Application {
          public static void main(String[] args) {
              //new
               Outer  outer = new Outer();
               //通过这个外部类来实例化内部类
              Outer.Inner inner = outer.new Inner();
              inner.in();
              inner.getID();
          }
      }
      
    2. 静态内部类

      public static  class Inner{
           public void in(){
               System.out.println("这是内部类的方法");
           }
      
    3. 局部内部类

      public class Outer {
      
          //局部内部类
          public void method(){
              class Inner{
                  public void in(){
                      
                  }
              }
          }
       }
      
    4. 匿名内部类

      public class Test {
          public static void main(String[] args){
              //没有名字初始化类,不用将实例保存到变量中
              new Apple().eat();
      //UserService userService = new UserService()
              new UserService(){
                  @Override
                  public void hello() {
                      
                  }
              };
          }
      }
      class Apple{
          public void eat(){
              System.out.println("1");
          }
      }
      interface UserService{
      void hello();
      }
      

异常机制

  • 异常(Exception) 指程序运行中出现的不期而至的各种状况,如:文件找不到,网络连接失败,非法参数等

  • 异常发生在程序运行期间,它影响了正常的程序执行流程。

  • 异常类型

    1. 检查性异常:最具代表的检查性异常是用户错误或问题引起的异常
    2. 运行时异常:运行时异常是可能被程序员避免的异常,与检查性异常相反,运行时异常可以在编译时被忽略
    3. 错误(ERROR):错误不是异常,而是脱离程序员控制的问题。比如,当栈溢出时,一个错误就发生了,在编译时时检查不到的。
  • Java 把异常当作对象来处理,并定义一个基类java.lang.Throwable作为所有异常的超类

  • 在Java API中已经定义了许多异常,这些异常分为两大类,错误Error和异常Exception
    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-enfGjx4c-1645525492610)(h在这里插入图片描述]
    ttps://img-blog.csdnimg.cn/6067c1ae497747e2a5d253f5b2e69990.png?x-oss-process=image/watermark,type_d3F5LXplbmhlaQ,shadow_50,text_Q1NETiBA5Y-q5oOz5q-P5aSp5YGl5bq355qE5p2O5p-Q5Lq6,size_20,color_FFFFFF,t_70,g_se,x_16#pic_center)

    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-LnIqkgeO-1645524917065)(C:\Users\Lr\AppData\Roaming\Typora\typora-user-images\image-20220124114642244.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-zAD9cnWW-1645524917066)(C:\Users\Lr\AppData\Roaming\Typora\typora-user-images\image-20220124120325869.png)]

  1. Error类对象由Java虚拟机生成并抛出,大多数错误与代码编写者所执行的操作无关
  2. Java虚拟机运行错误(Virtual MachineError),当JVM不再有继续执行操作所需的内存资源时,将出现OutOfMemoryErrror.这些异常发生时,Java虚拟机(JVM)一般会选择线程终止
  3. 发生在虚拟机试图执行应用时,如类定义错误(NoClassDefFoundError)、链接错误(LinkageError).这些错误不可查,因为它们在应用程序的控制和处理能力之外,而且绝大多数是程序运行时不允许出现的状况。
public class Test {
    public static void main(String[] args){
        int a = 1;
        int b = 0;
//假设要捕获多个异常:从小到大
        try{ //try监控区域
            System.out.println(a/b);
        }catch (ArithmeticException e){//catch(其中Throwable最高) 捕获异常
            System.out.println("程序出现异常,变量b不能为0");
        }finally {//处理善后工作
            System.out.println("finally");
        }

        //finally 可以不要finally
    }
}
测试结果:
    程序出现异常,变量b不能为0
    finally

        
  自动捕获   // 选中要捕获的然后Ctrl + Alt +T      

throw throws

public class Test {
    public static void main(String[] args){
       new Test().test(1,0);
    }

    public void test(int a, int b){
        if (b==0){
            throw new ArithmeticException();//主动抛出异常,一般在方法中使用
        }
    }
}
public class Test {
    public static void main(String[] args){
        //使用try catch可以捕获异常 不会使程序终止,会使程序运行下去
        try {
            new Test().test(1,0);
        } catch (ArithmeticException e) {
            e.printStackTrace();
        } 
    }

    //假设这个方法中,处理不了这个异常。方法上抛出异常
    public void test(int a, int b) throws ArithmeticException{
        if (b==0){
            throw new ArithmeticException();//主动抛出异常,一般在方法中使用
        }
    }
 }
    

自定义异常

  • 使用Java内置的异常类可以描述在编程时出现的大部分异常情况,用户还可以自定义异常。用户自定义异常类,只需继承Exception类
  • 在程序中使用自定义异常类
    1. 创建自定义异常类
    2. 在方法中通过throw关键字抛出异常对象
    3. 如果在当前抛出异常的方法中处理异常,可以使用try-catch语句捕获并处理;否则在方法的声明处通过throws关键字指明要抛出给方法调用者的异常,继续进行下一步操作
    4. 在出现异常方法的调用者中捕获并处理异常。
//自定义的异常类
public class MyException  extends Exception{
 //传递数字>10
    private int detail;

    public MyException(int a){
       this. detail = a;
    }
    //toString:异常的打印信息

    @Override
    public String toString() {
        return "MyException{" + "detail=" + detail + '}';
    }
}
public class Test {
    //可能会存在异常的方法
    static void test(int a) throws MyException {
        System.out.println("传递的参数为:"+a);
         if (a>10) {
             throw new MyException(a);//抛出  这里抛出 则外面的throws要捕获
        }
         System.out.println("OK");
    }
    public static void main(String[] args) {
        try {
            test(11);
        } catch (MyException e) {
            System.out.println("MyException=>" +e);
        }
    }
}
//自定义的异常类
public class MyException  extends Exception{
 //传递数字>10
    private int detail;

    public MyException(int a){
       this. detail = a;
    }
    //toString:异常的打印信息

    @Override
    public String toString() {
        return "MyException{" + "detail=" + detail + '}';
    }
}
public class Test {
    //可能会存在异常的方法
    static void test(int a) throws MyException {
        System.out.println("传递的参数为:"+a);
         if (a>10) {
             throw new MyException(a);//抛出  这里抛出 则外面的throws要捕获
        }
         System.out.println("OK");
    }
    public static void main(String[] args) {
        try {
            test(11);
        } catch (MyException e) {
            System.out.println("MyException=>" +e);
        }
    }
}
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值