zoukankan      html  css  js  c++  java
  • Java基础语法09-面向对象下-内部类-注解-异常

    内部类

    将一个类A定义在另一个类B里面,里面的那个类A就称为内部类,B则称为外部类

    (1)成员内部类:声明在外部类中方法外

    • 静态成员内部类

    • 非静态成员内部类

    (2)局部内部类:声明在外部类的方法体中

    • 有名字的局部内部类

    • 匿名的内部类

    静态内部类

    1、语法格式:

    【修饰符】 class 外部类 【extends 父类】 【implements 接口们】{
      【其他修饰符】 static class 静态内部类 【extends 父类】 【implements 接口们】{
       }
    }

    外部类的权限修饰符:public或缺省,其他修饰符:abstract或final

    静态内部类的权限修饰符:四种,其他修饰符:abstract或final + static

    2、静态内部类也是类

    (1)可以有自己的父类或父接口

    (2)有自己的字节码文件:外部类名$静态内部类名.class

    (3)有自己的成员:没有限制

    只要在类中可以写的成员它都可以有,只有静态内部类允许有静态成员。

    3、静态内部类的使用

    (1)静态内部类使用外部类的成员时:

    有限制:静态内部类不能使用外部类的非静态成员

    (2)在外部类中使用静态内部类

    使用静态内部类的静态成员:直接使用“静态内部类名."

    使用静态内部类的非静态成员:使用“静态内部类的对象."

    (3)在外部类的外面使用静态内部类

    前提:这个静态内部类在外面是可见,否则只能通过这个静态内部类的父类或父接口来引用它的对象。

    如果可见,使用静态内部类的静态成员:直接使用“外部类名.静态内部类名."

    使用静态内部类的非静态成员:使用“静态内部类的对象."

    外部类.静态内部类  对象名 = new  外部类.静态内部类(【...】);

    非静态内部类

    1、语法结构:

    【修饰符】 class 外部类 【extends 父类】 【implements 接口们】{
      【其他修饰符】 class 非静态内部类 【extends 父类】 【implements 接口们】{
       }
    }

    外部类的权限修饰符:public或缺省,其他修饰符:abstract或final

    非静态内部类的权限修饰符:四种,其他修饰符:abstract或final

    2、非静态内部类也是类

    (1)可以有自己的父类或父接口

    (2)有自己的字节码文件:外部类名$非静态内部类名.class

    (3)有自己的成员:有限制

    不能有静态成员,除非静态常量。

    3、非静态内部类的使用

    (1)非静态内部类使用外部类的成员时:没有限制

    (2)在外部类中使用非静态内部类

    在外部类的静态成员中使用无法使用非静态内部类的。

    在外部类的非静态成员中使用非静态内部类,使用“非静态内部类的对象."

    在非静态内部类的方法中有两个this对象,一个是外部类的this对象,一个是内部类的this对象

    (3)在外部类的外面使用非静态内部类

    前提:这个非静态内部类在外面是可见,否则只能通过这个非静态内部类的父类或父接口来引用它的对象。

    如果可见,使用非静态内部类的非静态成员:要求必须有外部类的对象的引用

    外部类 out = new 外部类(【...】);
    外部类.非静态内部类 对象名 = out.new 非静态内部类(【...】);

    //在实际开发中,在外部类中编写一个方法来返回非静态内部类的对象,然后调用这个方法来获取非静态内部类对象

    局部内部类

    【修饰符】 class 外部类 【extends 父类】 【implements 接口们】{
      【修饰符】 返回值类型 方法名(【形参列表】){
        【abstract或final或没有】 class 局部内部类 【extends 父类】 【implements 接口们】{
         }
       }
    }

    外部类的权限修饰符:public或缺省,其他修饰符:abstract或final

    局部内部类没有权限修饰符,其他修饰符:abstract或final

    局部内部类的特点:

    • 和外部类一样,它只是定义在外部类的某个方法中的另一个完整的类结构

      • 可以继承自己的想要继承的父类,实现自己想要实现的父接口们,和外部类的父类和父接口无关

      • 可以在局部内部类中声明属性、方法、构造器等结构,但不包括静态成员,除非是从父类继承的或静态常量

      • 可以使用abstract修饰,因此它也可以被同一个方法的在它后面的其他内部类继承

      • 可以使用final修饰,表示不能被继承

      • 编译后有自己的独立的字节码文件,只不过在内部类名前面冠以外部类名、$符号、编号。

        • 这里有编号是因为同一个外部类中,不同的方法中存在相同名称的局部内部类

    • 和成员内部类不同的是,它前面不能有权限修饰符等

    • 局部内部类如同局部变量一样,有作用域

    • 局部内部类中是否能访问外部类的静态还是非静态的成员,取决于所在的方法

    • 局部内部类中还可以使用所在方法的局部常量,即用final声明的局部变量

      • JDK1.8之后,如果某个局部变量在局部内部类中被使用了,自动加final

    在外部类中使用局部内部类

    有作用域,即只能在这个方法体中,并且在声明之后。

    在外部类的外面使用局部内部类:不能

    在外部类的外面可以得到局部内部类的对象

    但是需要通过它的父类或父接口的变量来引用,用方法的返回值返回。

    匿名内部类

    匿名内部类是没有名字的类,因此在声明类的同时就创建好了唯一的对象。

    匿名内部类的对象一般会三种形式使用它

    父类/父接口 变量 = new 父类/父接口(【实参列表】){
      //可以写方法....
    };

    new 父类/父接口(【实参列表】){
      //可以写方法....
    }.方法(【实参列表】);

    方法名(new 父类/父接口(【实参列表】){
      //可以写方法....
    });

    所有局部内部类的限制都适用于匿名内部类。例如:

    • 在匿名内部类中是否可以使用外部类的非静态成员变量,看所在方法是否静态

    • 在匿名内部类中如果需要访问当前方法的局部变量,该局部变量需要加final

    思考:这个对象能做什么呢?

    答:(1)调用某个方法(2)赋值给父类/父接口的变量,通过多态引用使用这个对象(3)作为某个方法调用的实参

    注解

    和普通注释不同:注解的注释内容是可以被另一段程序读取的

    一个完整的注解应该有三个部分:

    (1)声明: @interface

    (2)使用: @注解名 或 @注解名(....)

    (3)读取:

    • SOURCE:只能由编译器读取

    • CLASS:可以由类加载器读取

    • RUNTIME:可以通过反射的代码在运行时读取

    系统预定义的三个最基本的注解

    1、@Override

    用于检测被修饰的方法为有效的重写方法,如果不是,则报编译错误!

    只能标记在方法上。

    2、@Deprecated

    用于表示被标记的数据已经过时,不建议使用。

    可以用于修饰 属性、方法、构造、类、包、局部变量、参数。

    3、@SuppressWarnings

    抑制编译警告。

    可以用于修饰类、属性、方法、构造、局部变量、参数

    格式:

    @SuppressWarnings("all")
    @SuppressWarnings("uncheck")
    @SuppressWarnings({"unused","uncheck"})

    文档注释

    • @author 标明开发该类模块的作者,多个作者之间使用,分割

    • @version 标明该类模块的版本

    • @see 参考转向,也就是相关主题

    • @since 从哪个版本开始增加的

    • @param 对方法中某参数的说明,如果没有参数就不能写

    • @return 对方法返回值的说明,如果方法的返回值类型是void就不能写

    • @throws/@exception 对方法可能抛出的异常进行说明 ,如果方法没有用throws显式抛出的异常就不能写

      • 其中 @param @return 和 @exception 这三个标记都是只用于方法的。

      • @param的格式要求:@param 形参名 形参类型 形参说明

      • @return 的格式要求:@return 返回值类型 返回值说明

      • @exception 的格式要求:@exception 异常类型 异常说明

      • @param和@exception可以并列多个

    javadoc.exe就是这些注解的信息处理流程。

    如果导出时有乱码问题,可以指定字符编码

    -docencoding UTF-8
    -encoding UTF-8
    -charset UTF-8

    JUnit单元测试

    • @Test:标记在非静态的测试方法上。
    • @BeforeClass:标记在静态方法上。因为这个方法只执行一次。在所有方法@Test方法之前执行。

    • @AfterClass:标记在静态方法上。因为这个方法只执行一次。在所有方法@Test方法完成后执行。

    • @Before:标记在非静态方法上。在@Test方法前面执行,而且是在每一个@Test方法前面都执行

    • @After:标记在非静态方法上。在@Test方法后面执行,而且是在每一个@Test方法后面都执行

    • @BeforeClass、@AfterClass、@Before、@After都是配合@Test使用的,单独使用没有意义。

    元注解

    (1)@Target:用于描述注解的使用范围

    • 可以通过枚举类型ElementType的10个常量对象来指定

    (2)@Retention:用于描述注解的生命周期

    • 可以通过枚举类型RetentionPolicy的3个常量对象来指定

    • 唯有RUNTIME阶段才能被反射读取到。

    (3)@Documented:表明这个注解应该被 javadoc工具记录。

    (4)@Inherited:允许子类继承父类中的注解

    自定义注解

    @元注解
    【修饰符】 @interface 注解名{
      数据类型 参数名1();
      数据类型 参数名2() default 默认值;
    }

    (1)声明时,类型有要求:

    8种基本数据类型、String、枚举、Class、注解,以及他们的数组

    (2)使用时

    可以在定义 Annotation 的成员变量时为其指定初始值, 指定成员变量的初始值可使用 default 关键字

    如果定义的注解含有配置参数,那么使用时必须指定参数值,除非它有默认值。格式是“参数名 = 参数值”,如果只有一个参数成员需要赋值,且名称为value,可以省略“value=”

    自定义注解必须配上注解的信息处理流程才有意义。

    异常

    对于异常,一般有两种解决方法:一是遇到错误就终止程序的运行。另一种方法是由程序员在编写程序时,就考虑到错误的检测、错误消息的提示,以及错误的处理。

    异常的根类是java.lang.Throwable,其下有两个子类:java.lang.Errorjava.lang.Exception,平常所说的异常指java.lang.Exception

    如果要自定义异常,必须继承Throwable或它的子类

    Error:严重错误Error,无法通过处理的错误,只能事先避免

    Exception:表示异常,其它因编程错误或偶然的外在因素导致的一般性问题,程序员可以通过代码的方式纠正,使程序继续运行,是必须要处理的。

    Exception的两大类:编译时异常和运行时异常

    运行时异常:RuntimeException或它的子类

    编译时异常:除了运行时异常都是编译时异常

    Java异常处理的五个关键字:try、catch、finally、throw、throws

    1、try:尝试执行可能会发生异常的代码

    2、catch:尝试捕获try中发生的异常

    3、finally:无论try中是否发生异常,也无论catch是否可以捕获异常,也不管try和catch中是否有return语句,都要执行。除非在try或catch中执行了System.exit(0)语句。

    4、throw:用于手动抛出异常

    5、throws:表示某个方法内部没有处理xx异常,抛给调用者处理,在方法的签名中显式声明抛出哪些异常

    try{
      可能发生异常的代码
    }catch(异常类型 e){
      处理异常的代码
      //打印,或什么都不写,或者其他处理代码
    }catch(异常类型 e){
      处理异常的代码
      //打印,或什么都不写,或者其他处理代码
    }finally{
      ...
    }

    throw用在方法内,用来抛出一个异常对象,将这个异常对象传递到调用者处,并结束当前方法的执行。

    throw new 异常类名(参数);

    关键字throws运用于方法声明之上,用于表示当前方法不处理异常,而是提醒该方法的调用者来处理异常(抛出异常).

    修饰符 返回值类型 方法名(参数) throws 异常类名1,异常类名2…{   }

    在方法中使用try-catch的语句块来处理异常。

    try:该代码块中编写可能产生异常的代码。

    catch:用来进行某种异常的捕获,实现对捕获到的异常进行处理。

    • 可以有多个catch块,按顺序匹配。

    • 如果多个异常类型有包含关系,那么小上大下

    finally:有一些特定的代码无论异常是否发生,都需要执行。另外,因为异常会引发程序跳转,导致有些语句执行不到。而finally就是解决这个问题的,在finally代码块中存放的代码都是一定会被执行的。

    注意:finally不能单独使用。当只有在try或者catch中调用退出JVM的相关方法,例如System.exit(0),此时finally才不会执行,否则finally永远会执行。

    一般我们是使用一次捕获多次处理方式

    注意:这种异常处理方式,要求多个catch中的异常不能相同,并且若catch中的多个异常之间有子父类异常的关系,那么子类异常要求在上面的catch处理,父类异常在下面的catch处理。

    • 运行时异常被抛出可以不处理。即不捕获也不声明抛出。

    • 如果finally有return语句,永远返回finally中的结果,避免该情况.

    • 如果父类抛出了多个异常,子类重写父类方法时,抛出和父类相同的异常或者是父类异常的子类或者不抛出异常。

    • 父类方法没有抛出异常,子类重写父类该方法时也不可抛出异常。此时子类方法中产生了编译时异常,只能捕获处理,不能声明抛出

    自定义异常

    要求

    1、必须继承Throwable或它的子类,一般继承Exception或RuntimeException

    2、尽量保留两个构造器:无参和有参(message)

    3、加序列化版本ID

    4、自定义异常类型的对象只能使用throw语句抛出

    自定义异常最重要的是异常类的名字,当异常出现时,可以根据名字判断异常类型。

     常见异常列表

  • 相关阅读:
    paip.云计算以及分布式计算的区别
    paip.索引的种类以及实现attilax 总结
    paip.分布式应用系统java c#.net php的建设方案
    paip.提升性能--多核编程中的java .net php c++最佳实践 v2.0 cah
    paip.中文 分词 ---paoding 3.1 的使用
    paip.2013年技术趋势以及热点 v2.0 cae
    paip.为什么使用多线程的原因.
    paip.提升性能--多核cpu中的java/.net/php/c++编程
    paip.重装系统需要备份的资料总结..v2.0 cad
    paip.禁用IKAnalyzer 的默认词库.仅仅使用自定义词库.
  • 原文地址:https://www.cnblogs.com/Open-ing/p/11908168.html
Copyright © 2011-2022 走看看