Java 学习(10):java 异常处理
java 异常处理
异常发生的原因有很多,通常包含以下几大类:
- 用户输入了非法数据。
- 要打开的文件不存在。
- 网络通信时连接中断,或者JVM内存溢出。
三种类型的异常:
- 检查性异常: 最具代表的检查性异常是用户错误或问题引起的异常,这是程序员无法预见的。例如要打开一个不存在文件时,一个异常就发生了,这些异常在编译时不能被简单地忽略。 不处理编译不能通过。
- 运行时异常: 运行时异常是可能被程序员避免的异常。与检查性异常相反,运行时异常可以在编译时被忽略。
- 错误: 错误不是异常,而是脱离程序员控制的问题。错误在代码中通常被忽略。例如,当栈溢出时,一个错误就发生了,它们在编译也检查不到的。
通用异常: 在Java中定义了两种类型的异常和错误。
- JVM(Java虚拟机) 异常:由 JVM 抛出的异常或错误。例如:NullPointerException 类,ArrayIndexOutOfBoundsException 类,ClassCastException 类。
- 程序级异常:由 程序 或者 API程序 抛出的异常。例如 IllegalArgumentException 类,IllegalStateException 类。
所有的异常类是从 java.lang.Exception 类继承的子类。继承类如下:
Java 程序通常不捕获错误。错误一般发生在严重故障时,它们在Java程序处理的范畴之外。Error 用来指示运行时环境发生的错误。例如,JVM 内存溢出。一般地,程序不会从错误中恢复。
异常类有两个主要的子类:IOException 类和 RuntimeException 类。
Java 内置异常类:
- Java 语言定义了一些异常类在 java.lang 标准包中。
- 标准运行时异常类的子类是最常见的异常类。由于 java.lang 包是默认加载到所有的 Java 程序的,所以大部分从运行时异常类继承而来的异常都可以直接使用。
ArithmeticException 当出现异常的运算条件时,抛出此异常。例如,一个整数"除以零"时,抛出此类的一个实例。
ArrayIndexOutOfBoundsException 用非法索引访问数组时抛出的异常。如果索引为负或大于等于数组大小,则该索引为非法索引。
ArrayStoreException 试图将错误类型的对象存储到一个对象数组时抛出的异常。
ClassCastException 当试图将对象强制转换为不是实例的子类时,抛出该异常。
IllegalArgumentException 抛出的异常表明向方法传递了一个不合法或不正确的参数。
IllegalMonitorStateException 抛出的异常表明某一线程已经试图等待对象的监视器,或者试图通知其他正在等待对象的监视器而本身没有指定监视器的线程。
IllegalStateException 在非法或不适当的时间调用方法时产生的信号。换句话说,即 Java 环境或 Java 应用程序没有处于请求操作所要求的适当状态下。
IllegalThreadStateException 线程没有处于请求操作所要求的适当状态时抛出的异常。
IndexOutOfBoundsException 指示某排序索引(例如对数组、字符串或向量的排序)超出范围时抛出。
NegativeArraySizeException 如果应用程序试图创建大小为负的数组,则抛出该异常。
NullPointerException 当应用程序试图在需要对象的地方使用 null 时,抛出该异常
NumberFormatException 当应用程序试图将字符串转换成一种数值类型,但该字符串不能转换为适当格式时,抛出该异常。
SecurityException 由安全管理器抛出的异常,指示存在安全侵犯。
StringIndexOutOfBoundsException 此异常由 String 方法抛出,指示索引或者为负,或者超出字符串的大小。
UnsupportedOperationException 当不支持请求的操作时,抛出该异常。
Java 的非检查性异常
ClassNotFoundException 应用程序试图加载类时,找不到相应的类,抛出该异常。
CloneNotSupportedException 当调用 Object 类中的 clone 方法克隆对象,但该对象的类无法实现 Cloneable 接口时,抛出该异常。
IllegalAccessException 拒绝访问一个类的时候,抛出该异常。
InstantiationException 当试图使用 Class 类中的 newInstance 方法创建一个类的实例,而指定的类对象因为是一个接口或是一个抽象类而无法实例化时,抛出该异常。
InterruptedException 一个线程被另一个线程中断,抛出该异常。
NoSuchFieldException 请求的变量不存在
NoSuchMethodException 请求的方法不存在
Java 定义在 java.lang 包中的检查性异常类
异常方法:
public String getMessage()
返回关于发生的异常的详细信息。这个消息在Throwable 类的构造函数中初始化了。
public Throwable getCause()
返回一个Throwable 对象代表异常原因。
public String toString()
使用getMessage()的结果返回类的串级名字。
public void printStackTrace()
打印toString()结果和栈层次到System.err,即错误输出流。
public StackTraceElement [] getStackTrace()
返回一个包含堆栈层次的数组。下标为0的元素代表栈顶,最后一个元素代表方法调用堆栈的栈底。
public Throwable fillInStackTrace()
用当前的调用栈层次填充Throwable 对象栈层次,添加到栈层次任何先前信息中。
以下是Throwable 类的主要方法
捕获异常:
使用 try 和 catch 关键字可以捕获异常。语法:
try{
// 程序代码
}catch(ExceptionName e1){ //Catch 语句包含要捕获异常类型的声明。当保护代码块中发生一个异常时,try 后面的 catch 块就会被检查
//Catch 块
}
eg:
/* 文件名 : ExcepTest.java
该例中声明有两个元素的一个数组,当代码试图访问数组的第三个元素的时候就会抛出一个异常 */
import java.io.*;
public class ExcepTest{ public static void main(String args[]){
try{
int a[] = new int[];
System.out.println("Access element three :" + a[]);
}catch(ArrayIndexOutOfBoundsException e){
System.out.println("Exception thrown :" + e);
}
System.out.println("Out of the block");
}
}
数组访问溢出异常 实例
多重捕获块:一个 try 代码块后面跟随多个 catch 代码块的情况就叫多重捕获,语法
try{
// 程序代码
}catch(异常类型1 异常的变量名1){
// 程序代码
}catch(异常类型2 异常的变量名2){
// 程序代码
}catch(异常类型2 异常的变量名2){
// 程序代码
} /* 如果保护代码中发生异常,异常被抛给第一个 catch 块,如果抛出异常的数据类型与 ExceptionType1 匹配,它在这里就会被捕获; 如果不匹配,它会被传递给第二个 catch 块; 如此,直到异常被捕获或者通过所有的 catch 块 */
catch 多重捕获块 语法
throws/throw 关键字(抛出异常) & finally 关键字:
- 如果一个方法没有捕获一个检查性异常,那么该方法必须使用 throws 关键字来声明。throws 关键字放在方法签名的尾部。若抛出多个异常,多个异常之间用逗号隔开。
- 也可以使用 throw 关键字抛出一个异常,无论它是新实例化的还是刚捕获到的。
import java.io.*;
public class className{
public void deposit(double amount) throws RemoteException{
// Method implementation
throw new RemoteException();
}
//Remainder of class definition
}eg:抛出一个 RemoteException 异常
finally 关键字:用来创建在 try 代码块后面执行的代码块。无论是否发生异常,finally 代码块中的代码总会被执行。在 finally 代码块中,可以运行清理类型等收尾善后性质的语句。
public class ExcepTest{
public static void main(String args[]){
int a[] = new int[];
try{
System.out.println("Access element three :" + a[]);
}catch(ArrayIndexOutOfBoundsException e){
System.out.println("Exception thrown :" + e);
}
finally{
a[] = ;
System.out.println("First element value: " +a[]);
System.out.println("The finally statement is executed");
}
}
}try...catch...finally 实例
注意下面事项:
- catch 不能独立于 try 存在。
- 在 try/catch 后面添加 finally 块并非强制性要求的。
- try 代码后不能既没 catch 块也没 finally 块。
- try, catch, finally 块之间不能添加任何代码。
声明自定义异常:
自定义异常需要注意一下几点:
- 所有异常都必须是 Throwable 的子类。
- 如果希望写一个检查性异常类,则需要继承 Exception 类。如下:
class MyException extends Exception{}
- 如果你想写一个运行时异常类,那么需要继承 RuntimeException 类。
- 一个异常类和其它任何类一样,包含有变量和方法。
以下实例是一个银行账户的模拟,通过银行卡的号码完成识别,可以进行存钱和取钱的操作。
// 文件名InsufficientFundsException.java
import java.io.*; //自定义异常类,继承Exception类
public class InsufficientFundsException extends Exception
{
//此处的amount用来储存当出现异常(取出钱多于余额时)所缺乏的钱
private double amount;
public InsufficientFundsException(double amount)
{
this.amount = amount;
}
public double getAmount()
{
return amount;
}
}InsufficientFundsException.java - 自定义异常类 文件代码:
为了展示如何使用我们自定义的异常类,在下面的 CheckingAccount 类中包含一个 withdraw() 方法抛出一个 InsufficientFundsException 异常。
// 文件名称 CheckingAccount.java
import java.io.*; //此类模拟银行账户
public class CheckingAccount
{
//balance为余额,number为卡号
private double balance;
private int number;
public CheckingAccount(int number)
{
this.number = number;
}
//方法:存钱
public void deposit(double amount)
{
balance += amount;
}
//方法:取钱
public void withdraw(double amount) throws
InsufficientFundsException
{
if(amount <= balance)
{
balance -= amount;
}
else
{
double needs = amount - balance;
throw new InsufficientFundsException(needs);
}
}
//方法:返回余额
public double getBalance()
{
return balance;
}
//方法:返回卡号
public int getNumber()
{
return number;
}
}CheckingAccount.java - 使用上述自定义的文件类 文件代码:
下面的 BankDemo 程序示范了如何调用 CheckingAccount 类的 deposit() 和 withdraw() 方法。
//文件名称 BankDemo.java
public class BankDemo
{
public static void main(String [] args)
{
CheckingAccount c = new CheckingAccount();
System.out.println("Depositing $500...");
c.deposit(500.00);
try
{
System.out.println("\nWithdrawing $100...");
c.withdraw(100.00);
System.out.println("\nWithdrawing $600...");
c.withdraw(600.00);
}catch(InsufficientFundsException e)
{
System.out.println("Sorry, but you are short $"
+ e.getAmount());
e.printStackTrace();
}
}
}BankDemo.java - 调用 CheckingAccount 类的方法 文件代码:
编译上面三个文件,并运行程序 BankDemo,得到结果如下所示:
Depositing $... Withdrawing $... Withdrawing $...
Sorry, but you are short $200.0
InsufficientFundsException
at CheckingAccount.withdraw(CheckingAccount.java:)
at BankDemo.main(BankDemo.java:)
Pre-article:Java 学习(9):java Stream & File & IO
Next:Java 学习(11): 面向对象编程—继承(super,this)
Java 学习(10):java 异常处理的更多相关文章
- [java学习笔记]java语言核心----面向对象之构造函数
1.构造函数概念 特点: 函数名与类名相同 不用定义返回值类型 没有具体的返回值 作用: 给对象进行初始化 注意: 默认构造函数 多个构造函数是以重载出现的 一个类中如果 ...
- [ Java学习基础 ] Java的继承与多态
看到自己写的东西(4.22的随笔[ Java学习基础 ] Java构造函数)第一次达到阅读100+的成就还是挺欣慰的,感谢大家的支持!希望以后能继续和大家共同学习,共同努力,一起进步!共勉! ---- ...
- [java学习笔记]java语言核心----面向对象之this关键字
一.this关键字 体现:当成员变量和函数的局部变量重名时,可以使用this关键字来区别:在构造函数中调用其它构造函数 原理: 代表的是当前对象. this就是所在函数 ...
- [ Java学习基础 ] Java构造函数
构造方法是类中特殊方法,用来初始化类的实例变量,它在创建对象(new运算符)之后自动调用. Java构造方法的特点如下: 构造方法名必须与类名相同. 构造方法没有任何返回值,包括void. 构造方法只 ...
- [ Java学习基础 ] Java的抽象类与接口
一.抽象类 1. 抽象类 Java语言提供了两种类:一种是具体类:另一种是抽象子类. 2. 抽象类概念: 在面向对象的概念中,所有的对象都是通过类来描绘的,但是反过来,并不是所有的类都是用来描绘对象的 ...
- [ Java学习基础 ] Java异常处理
一.异常概述 异常是程序中的一些错误,但并不是所有的错误都是异常,并且错误有时候是可以避免的.比如说,你的代码少了一个分号,那么运行出来结果是提示是错误 java.lang.Error:如果你用Sys ...
- Java学习10——package和import
package和import语句 为了便于管理大型软件系统中数目众多的类,解决类的命名冲突问题,Java引入包(package)机制,提供类的多重类命名空间,使用时,import引入相应package ...
- java学习路线图-----java基础学习路线图(J2SE学习路线图)
安装JDK和开发软件跳过,网上太多了,不做总结,以下是我总结的学习路线图,欢迎补充. JAVA基础语法 注释,标识符命名规则及Java中的关键字 Java基本数据类型 Java运算符与表达式 Java ...
- Java学习笔记 -- Java定时调度工具Timer类
1 关于 (时间宝贵的小姐姐请跳过) 本教程是基于Java定时任务调度工具详解之Timer篇的学习笔记. 什么是定时任务调度 基于给定的时间点,给定的时间间隔或者给定的执行次数自动执行的任务. 在Ja ...
- 最全Java学习路线图——Java学习指南
准备篇 适用/适合人群:适合基础小白 目标:掌握JavaSE. ●技术点小节: 1.开发工具的安装配置的介绍 2.JDK安装 3.DOS环境编程 4.Eclipse的安装使用 ●JAVA基础 1.基本 ...
随机推荐
- cogs 306. [SGOI] 糊涂的记者
306. [SGOI] 糊涂的记者 ★★★ 输入文件:sign.in 输出文件:sign.out 评测插件时间限制:1 s 内存限制:128 MB [问题描述] 在如今的信息社会中,时 ...
- HDU 2815
特判B不能大于等于C 高次同余方程 #include <iostream> #include <cstdio> #include <cstring> #includ ...
- [Tailwind] Style Elements on hover and focus with Tailwind’s State Variants
In this lesson, we learn how to target specific states of elements and apply styles only when those ...
- Swift开发教程--怎样自己定义TabBarItem的图片显示
在做项目的时候,假设使用系统的UITabBarController的时候,底部的tab自己定义图片显示是蓝色和灰色的.这不是我们所想要的效果. 假设想显示自己定义的按下和弹起的图片效果.这个时候就须要 ...
- SQL语法精讲(包括建库、建表、建视图、查询、增加、删除、)
SQL语法精讲(包括建库.建表.建视图.查询.增加.删除.修改) SQL分类: DDL—数据定义语言(CREATE,ALTER,DROP,DECLARE) DML—数据操纵语言(SELECT,DELE ...
- hdu2476String painter (区间DP)
Problem Description There are two strings A and B with equal length. Both strings are made up of low ...
- Word技巧杂记(二)——批量修改修订格式并接受
今天的题目好奇怪啊,呵呵,起因如下: 今天老婆在修改论文,她的老板提出一个非常**的要求——把Word中所有修订后的文字用特殊的字体(蓝色)标出来,然后再接受修订.我勒个去,明明有修订后的模式啊,为什 ...
- Jenkins+Docker部署Maven聚合工程
这几天,把公司的预发布环境,改成docker部署,遇到了一些坑,有jenkins里的部署脚本的问题,也有harbor仓库的问题,还有docker远程访问的问题,还有DooD....一堆坑 Jenkin ...
- Redis学习笔记(八) 基本命令:SortedSet操作
原文链接:http://doc.redisfans.com/sorted_set/index.html SortedSet的数据结构类似于Set,不同的是Sorted中的每个成员都分配了一个值(Sco ...
- Solidworks.2016.SP5下载安装破解图文教程
安装此软件一定要断网安装!!!下载完成后解压文件,打开破解文件夹,双击文件夹中的SolidWorksSerialNumbers2016.reg进行注册表注册,如下图. 解压软件安装包(或者将软件安 ...