java内部类以及异常处理

框架图

java内部类以及异常处理

内部类

将一个类定义在另一个类的里面,里面那个类就称为内部类(也叫内置类或嵌套类)。

内部类的访问规则:
1。内部类可以直接访问外部类中的成员,包括私有成员。
    之所以可以直接访问外部类中的成员,是因为内部类中持有了一个外部类的引用,格式 外部类名.this
2。外部类要访问内部类,必须建立内部类对象。

 class  InnerClassDemo
{
public static void main(String[] args)
{
//外部其他类直接访问内部类中的成员。格式写法
Outer.Inner in = new Outer().new Inner();
in.function();
}
} class Outer
{
private int x = 3; class Inner//内部类定义在成员位置上
{ void function()
{
System.out.println("innner :"+x);//内部类可以直接访问外部类,相当于省略了Outer.this句柄。
}
} void method()
{
Inner in = new Inner();//外部类想访问内部类要先建立内部类对象。
in.function();
}
}

内部类定义在成员位置上
•可以被private static成员修饰符修饰。
•被static修饰的内部类只能访问外部类中的静态成员。

内部类定义在局部位置上
•也可以直接访问外部类中的成员。
•同时可以访问所在局部中的局部变量,但必须是被final修饰的。

匿名内部类

1,匿名内部类其实就是内部类的简写格式。
2,定义匿名内部类的前提:内部类必须继承一个类或者实现接口。但最多只能继承一个父类,或实现一个接口。
3,匿名内部类的格式:  new 父类或者接口(){定义子类的内容}
4,其实匿名内部类就是一个匿名子类对象,而且这个对象有点胖,可以理解为带内容的对象。
5,匿名内部类中定义的方法最好不要超过3个。
6,创建匿名内部类时会立即创建一个该类的实例,这个类定义立即消失,匿名内部类不能重复使用。

7,匿名内部类不能是抽象类,因为系统在创建匿名内部类的时候,会立即创建内部类的对象。因此不允许将匿名内部类定义成抽象类。
8,匿名内部类不能定义构造函数,因为匿名内部类没有类名,所以无法定义构造函数,但匿名内部类可以定义构造代码块,通过构造代码块来完成构造器需要完成的事情,也可以通过直接调用父类的构造方法实现初始化。

 abstract class AbsDemo{
abstract void show();}
class Outer
{
int x = 3;
/*
class Inner extends AbsDemo
{
int num = 90;
void show()
{
System.out.println("show :"+num);
}
void abc()
{
System.out.println("hehe");
}
}*/
public void function()
{
//new Inner().show(); new AbsDemo()//匿名内部类相当于以上绿色部分内部类简写。
{
int num = 9;
void show()
{
System.out.println("num==="+num);
}
void abc()
{
System.out.println("haha");
}
}.show();
}
}
class InnerClassDemo4
{
public static void main(String[] args)
{
new Outer().function();
}
}

异常

异常就是程序在运行时出现不正常情况。问题也是现实生活中一个具体的事物,也可以通过java的类的形式进行描述。并封装成对象,把问题封装成对象就是异常。
对于问题划分为两种:
一种是严重的问题(java通过Error类进行描述,对于Error一般不编写针对性的代码对其进行处理);
一种是非严重的问题(java通过Exception类进行描述,对于Exception可以使用针对性的处理方式进行处理)。

无论Error或者Exception都具有一些共性内容。
比如:不正常情况的信息,引发原因等。

Throwable是 Java 语言中所有错误和异常类的父类。
  |--Error
  |--Exception

异常的处理

java 提供了特有的语句进行处理。
try
{
    需要被检测的代码;
}
catch(异常类 变量)
{
    处理异常的代码;(处理方式)
}
finally
{
    一定会执行的语句,不管有没有异常都会执行;一般说,把需要关闭的资源放在这里。finally只有一种情况不会执行。当执行到System.exit(0);fianlly不会执行。

}

异常语句的格式

格式一:try{ }catch( ){ }finally{ }

格式二:try{ }catch( ){ }

格式三:try{ }finally{ }

格式四:try{ }catch( ){ } catch( ){ }catch( ){ }

异常的处理要么try,catch处理,要么声明throws抛出由调用者处理。示例代码:

  class Demo
{
int div(int a,int b)
{
return a/b;
}
}
class ExceptionDemo
{
public static void main(String[] args)
{
Demo d = new Demo();
try
{
int x = d.div(,);
//在出现异常的地方,终止执行代码,进入到catch。
System.out.println("x="+x);
}
catch (Exception e)//Exception e = new ArithmeticException();可以捕获所有异常,多态。
{
System.out.println("除零啦");
System.out.println(e.getMessage());//异常信息。 / by zero;
System.out.println(e);//异常名称 :异常信息。
e.printStackTrace(); //打印异常的堆栈的跟踪信息。异常名称,异常信息,异常出现的位置。
//jvm默认的异常处理机制,就是在调用printStackTrace方法。
} System.out.println("over"); }
}
class Demo
{
int div(int a,int b)throws Exception//在功能上通过throws的关键字声明了该功能有可能会出现问题。异常抛给调用者(主函数)去处理。
{
return a/b;
}
}
class ExceptionDemo
{
public static void main(String[] args)throws Exception//异常抛给JVM去处理。默认调用printStackTrace方法。
{
Demo d = new Demo();
int x = d.div(,);
System.out.println("x="+x);
}
}

对多异常的处理

1,声明异常时,建议声明更为具体的异常。这样处理的可以更具体。
2,对方声明几个异常,就对应有几个catch块。不要定义多余的catch块。 如果多个catch块中的异常出现继承关系,父类异常catch块放在最下面。
3,建立在进行catch处理时,catch中一定要定义具体处理方式。不要简单定义一句 e.printStackTrace(),也不要简单的就书写一条输出语句。

 class Demo
{
int div(int a,int b)throws ArithmeticException,ArrayIndexOutOfBoundsException//在功能上通过throws的关键字声明了该功能有可能会出现问题。
{ int[] arr = new int[a]; System.out.println(arr[]);
return a/b;
}
}
class ExceptionDemo2
{
public static void main(String[] args) throws Exception
{
Demo d = new Demo();
try
{
int x = d.div(,);
System.out.println("x="+x);
} catch (ArithmeticException e)//算术运算异常。
{
System.out.println(e.toString());
System.out.println("被零除了!!"); }
catch (ArrayIndexOutOfBoundsException e)//角标越界异常。
{
System.out.println(e.toString());
System.out.println("角标越界啦!!");
}
catch(Exception e)//多个catch块中的异常出现继承关系,父类异常catch块放在最下面。
{
System.out.println("hahah:"+e.toString());
} System.out.println("over");
}
}

自定义异常

因为项目中会出现特有的问题,而这些问题并未被java所描述并封装对象。所以对于这些特有的问题可以按照java的对问题封装的思想,将特有的问题进行自定义的异常封装。
自定义异常:
必须是自定义类继承Exception和RuntimeException。

如何定义异常信息呢?
因为父类中已经把异常信息的操作都完成了。
所以子类只要在构造时,将异常信息传递给父类通过super语句。
那么就可以直接通过getMessage方法获取自定义的异常信息。

 /*需求:在本程序中,对于除数是-1,也视为是错误的是无法进行运算的。那么就需要对这个问题进行自定义的描述。*/
class MyException extends Exception//自定义异常类继承Exception
{
private int value;
MyException(String msg,int value)//父类中已经把异常信息的操作都完成了,子类只要在构造时,将异常信息通过super语句传递给父类。
{
super(msg);
this.value = value;
}
public int getValue()//子类特有方法获取被除数(负数)
{
return value;
} }
class Demo
{
int div(int a,int b)throws MyException
{
if(b<)
throw new MyException("出现了除数是负数的情况------ / by negative number",b);//手动通过throw关键字抛出一个自定义异常对象。 return a/b;
}
}
class ExceptionDemo3
{
public static void main(String[] args)
{
Demo d = new Demo();
try
{
int x = d.div(,-);
System.out.println("x="+x);
}
catch (MyException e)
{
System.out.println(e.getMessage());
System.out.println("错误的负数是:"+e.getValue());
}
System.out.println("over");
}
}

throws和throw的区别
throws使用在函数上。
throw使用在函数内。

throws后面跟的异常类。可以跟多个。用逗号隔开。
throw后跟的是异常对象。

throw单独存在时,下面不能有执行语句,无法执行,无论是在主函数还是在一般函数,出现编译错误。形式和return、contiune、break一样。

当函数内有throw抛出异常对象时,并未进行try,catch处理,必须在函数上声明,否则编译失败。注意,RuntimeException除外。如果函数内抛出RuntimeException异常,函数上可以不用声明,编译一样通过。函数上抛出RuntimeException,可以处理也可不处理,编译一样通过。之所以不用在函数声明,是因为不需要让调用者处理。当该异常发生时,希望程序停止。因为在运行时,出现了无法继续运算的情况,希望停止程序后,对代码进行修正。

异常在子父类覆盖中的体现

1,子类在覆盖父类时,如果父类的方法抛出异常,那么子类的覆盖方法,只能抛出父类的异常或者该异常的子类。

2,如果父类方法抛出多个异常,那么子类在覆盖该方法时,只能抛出父类异常的子集。

3,如果父类或者接口的方法中没有异常抛出,那么子类在覆盖方法时,也不可以抛出异常。

如果子类方法发生了异常,就必须要进行try处理,绝对不能抛。

包(package)

对类文件进行分类管理。

给类提供多层命名空间。

写在程序文件的第一行。

类名的全称的是 包名.类名。

包也是一种封装形式。

包之间的访问

包与包之间进行访问,被访问的包中的类以及类中的成员,需要public修饰。

不同包中的子类还可以直接访问父类中被protected权限修饰的成员。

protected是为其他包中的子类提供的一种权限。

包与包之间可以使用的权限只有两种,public  protected。

public    protected    default     private

同一个类中     ok         ok             ok          ok

同一个包中     ok         ok             ok

子类             ok         ok

不同包中       ok

导包

为了简化类名的书写,使用一个关键字,import.import 导入的是包中的类。

建议,不要写通配符 * ,需要用到包中的哪个类,就导入哪个类。

建立定包名不要重复,可以使用url来完成定义,url是唯一的。例如:

www.itcast.cn

package cn.itcast.demo

package cn.itcast.test

Jar包的操作

通过jar.exe工具对jar的操作。

创建jar包jar -cvf mypack.jar packa packb

查看jar包jar -tvf mypack.jar [>定向文件]

解压缩jar -xvf mypack.jar

自定义jar包的清单文件jar –cvfm mypack.jar mf.txt packa packb

上一篇:深入理解Java虚拟机之Java内存区域随笔


下一篇:gradle第一篇:初入门