JDBC和异常总结及常见使用

JDBC

-一、JDBC连接过程

01.注册驱动

Class.forName("oracle.jdbc.driver.OracleDriver");

02.获取连接

Connection conn = DriverManager.getConnection("jdbc:oracle:thin:@10.0.19.252:1521:orcl","itxy","itxy");

-二、JDBC 常用接口

JDBC :   sun提供的访问数据库的规范

这套规范用于高速数据库厂商,通过何种方式访问他们的数据库

01.java.sql 接口 Connection

sun的JDBC是一套接口规范,没有提供实现 (JDBC的接口实现,只能由各个数据库厂商自己实现)

02.java.sql

接口 Statement   用于执行静态 SQL 语句并返回它所生成结果的对象。

java.sql

接口 PreparedStatement   表示预编译的 SQL 语句的对象。

注意:开发的时候首先 PreparedStatement

原因: 1. 预编译的 SQL 语句的对象运行速度快

2. 安全 (可以防止SQL注入攻击)

03.java.sql 接口 ResultSet

表示数据库结果集的数据表,通常通过执行查询数据库的语句生成。

  ResultSet 对象具有指向其当前数据行的光标。最初,光标被置于第一行之前。next 方法将光标移动到下一行;因为该方法在 ResultSet 对象没有下一行时返回 false,所以可以在
while 循环中使用它来迭代结果集。

默认的 ResultSet 对象不可更新,仅有一个向前移动的光标。因此,只能迭代它一次,并且只能按从第一行到最后一行的顺序进行。

-三、JDBC使用常见异常

java.lang

类 Class<T>

java.lang.ClassNotFoundException: oracle.jdbc.driver.OracleDriver2

数据库驱动未加载成功

java.sql.SQLException: The Network Adapter could not establish the connection

数据库连接串配置错误

java.sql.SQLException: ORA-01017: invalid username/password; logon denied

访问数据库的用户名或密码错误

异常总结

1. 异常的处理顺序,一定是子类异常处理在前,父类异常处理在后

try {
	biz.deleteStudent("s002");
	System.out.println("删除完毕!");
} catch (SQLIntegrityConstraintViolationException e) {

} catch (Exception e) {
	e.printStackTrace();
	System.out.println("系统异常,请检查");
}	

2. 在三层架构中,每层都可能出现异常,但是只有UI层采用最终的异常显示的决定权。

其它层可以捕获异常,但是处理后需要再次抛出!

3. 非托管资源(不受GC管理的资源),一定要在finally中释放,放在资源泄漏;

不受GC管理的资源:如数据连接Connection , 必须要用close()方法释放

还有IO流的释放,也必须使用close()

 try {

}finally{
	dao.closeConnection();
}

4. 自定义异常

public class HavaSonRecordsException extends Exception{

    public HavaSonRecordsException(String msg){
    	super(msg);
    }
}

5. java.lang 类 Throwable

直接已知子类:

Error, Exception

Error 是 Throwable 的子类,用于指示合理的应用程序不应该试图捕获的严重问题。

注意: Error无需用try catch

Error异常举例: 如内存越界、内存溢出

6. try catch   是可以嵌套使用的

7.只有try,没有catch

  try {
	dao.updateStuState(0, sno);
}finally{
	//释放IO流的句柄
	System.out.println("io资源释放");
}	

8. checked Exception 与 unChecked Exception(Runtime Exception)

checked Exception(特点:在编译期可以明确异常的可能发生的位置,而且必须要捕获它):

ClassNotFoundException

SQLException

Runtime Excepiton (编译期无法检查到这个异常,只有在程序运行期间才能知道):

NullExcepiton ,  10/0   , format("")

public class InputNullExcepiton extends RuntimeException{}   //RuntimeException无需强制处理

public class InputNullExcepiton extends Exception{}         //自定义异常,建议extends Exception

//数据库Connection是一种宝贵的资源,很容易称为业务系统的性能瓶颈

  使用原则:

晚打开,早关闭  -----  使用时间越短越好

Connection尽量可以重用

//数据库Connection的数量不是无限的,它受限于硬件(CPU)

补:

java.util 类 Date      //除了dao层之外,都尽量使用java.util.Date

java.sql 类 Date        //只能在dao层使用

练习(Java项目):

自定义异常

public class InputNullException extends Exception {
	public InputNullException(String msg){
		super(msg);
	}
}

web层

public class StuUI {

	/**
	 * 删除学生
	 */
	public static void deleteStuTest(){
		StuBiz biz = new StuBiz();
		try {
			biz.deleteStudent("s003234");
			System.out.println("删除完毕!");
		} catch (Exception e) {
			e.printStackTrace();
			System.out.println("系统异常,请检查");
		}
	}

	/**
	 * 添加学生
	 */
	public static void addStuTest(){
		StuBiz biz = new StuBiz();
		TStudent ts = new TStudent();

		ts.setSname("jack");
		ts.setSno("s002244");
		ts.setCno("c0124");
		ts.setSex("f");
		ts.setAddress("taiyuan");
		ts.setTel("155345263");

		String s = "2012-06-21";
		SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
		java.util.Date d1 = null;
		try {
			d1 = sdf.parse(s);
		} catch (ParseException e1) {
			e1.printStackTrace();
		} //先把字符串转为util.Date对象
		java.sql.Date d2 = new java.sql.Date(d1.getTime()); 
		ts.setBirthday(d2);

		ts.setHeight(54);
		ts.setState(1);

		try {
			biz.addStu(ts);
			System.out.println("添加学生成功!");
		} catch(InputNullException e){
			System.out.println("入参为空!");
		}catch (Exception e) {
			e.printStackTrace();
			System.out.println("插入失败!");
		}

	}

	/**
	 * 查询所有学生信息
	 */
	public static void showStu(){
		StuBiz biz = new StuBiz();
		try {
			List<TStudent> stus = biz.findAllStu();
			Iterator<TStudent> it = stus.iterator();
		    while(it.hasNext()){
		    	TStudent t = it.next();
		    	System.out.println(t.getSname() + "--" + t.getSno() + "--" + t.getBirthday());
		    }
		} catch (Exception e) {
			e.printStackTrace();
			System.out.println("查询失败!");
		}
	}

	public static void main(String[] args) {
		StuUI.showStu();
	}
}

业务逻辑层:

public class StuBiz {

	/**
	 * 删除学生
	 *    注意: 1. 当学生没有产生业务数据时,直接删除物理记录
	 *        2.  当学生产生了业务数据时,只能做逻辑删除
	 * @param sno
	 * @throws Exception
	 */
	public void deleteStudent(String sno) throws Exception{
		if(sno != null){
			StuDao dao = new StuDao();
			try {
				dao.deleteStudent(sno);
			}catch(java.sql.SQLIntegrityConstraintViolationException e){
			  if(e.getSQLState().equals("23000")){
				  //找到了子记录
				  try {
					  dao.updateStuState(0, sno);
				  } catch (Exception e2) {
					  e2.printStackTrace();
					  throw e2;
				  }finally{
					  dao.closeConnection();
				  }				  
			  }
			} catch (Exception e) {
				throw e;
			}finally{
				dao.closeConnection();
			}

		}else{
			throw new Exception("入参错误,sno=null");
		}

	}

	/**
	 * 添加学生
	 * @param ts
	 * @throws Exception
	 */
	public void addStu(TStudent ts) throws Exception{
		if(ts!=null){
			StuDao dao = new StuDao();
			try {
				boolean bet = dao.findClass(ts.getCno());
				if(!bet){
					throw new Exception("班级不存在");
				}else{
					dao.addStu(ts);
				}
			} catch (Exception e) {
				throw e;
			}finally {
				dao.closeConnection();
			}
		}else{
			throw new Exception("入参错误!");
		}
	}

	/**
	 * 查询所有学生信息
	 * @return
	 * @throws Exception
	 */
	public List<TStudent> findAllStu() throws Exception {
	 //注意:面向接口编程不能是实现类返回
		List<TStudent> stus;
		StuDao dao = new StuDao();
		try {
			stus = dao.findAllStu();
		} catch (Exception e) {
			throw e;
		}finally {
			dao.closeConnection();
		}

		return stus;
	}
}

数据层:

public class StuDao extends BaseDao{
	/**
	 * 删除学生
	 *    注意: 1. 当学生没有产生业务数据时,直接删除物理记录
	 *        2.  当学生产生了业务数据时,只能做逻辑删除
	 * @param sno
	 * @throws Exception
	 */
	public void deleteStudent(String sno) throws Exception{
		String sql = "delete from tstudent where sno=?";
		this.openConnection();
		PreparedStatement ps = this.conn.prepareStatement(sql);
		ps.setString(1, sno);
		ps.executeUpdate();
		ps.close();
	}

	/**
	 * 修改学生的状态值
	 * @param state
	 * @throws Exception
	 */
	public void updateStuState(int state,String sno) throws Exception{
		String sql = "update tstudent set state=? where sno=?";
		this.openConnection();
		PreparedStatement ps = this.conn.prepareStatement(sql);
		ps.setInt(1, state);
		ps.setString(2, sno);
		ps.executeUpdate();
		ps.close();

	}

	/**
	 * 添加学生
	 * @param ts
	 * @throws Exception
	 */
	public void addStu(TStudent ts) throws Exception {
		String sql = "insert into tstudent values(?,?,?,?,?,?,?,?,?)";
		//数据库打开
		this.openConnection();
		PreparedStatement ps = this.conn.prepareStatement(sql);
		ps.setString(1, ts.getSname());
		ps.setString(2, ts.getSno());
		ps.setString(3, ts.getCno());
		ps.setString(4, ts.getSex());
		ps.setString(5, ts.getAddress());
		ps.setString(6, ts.getTel());
		ps.setDate(7, ts.getBirthday());
		ps.setInt(8, ts.getHeight());
		ps.setInt(9, ts.getState());

		ps.executeUpdate();
		ps.close();
	}

	/**
	 * 添加学生的时候,检查班级是否存在
	 * @param cno
	 * @return
	 * @throws Exception
	 */
	public boolean findClass(String cno) throws Exception {
		boolean bRet = false;

		String sql = "select * from tclass where cno=?";
		this.openConnection();
		PreparedStatement ps = this.conn.prepareStatement(sql);
		ps.setString(1, cno);
		ResultSet rs = ps.executeQuery();
		while(rs.next()){
			bRet = true;
		}
		rs.close();
		ps.close();

		return bRet;
	}

	/**
	 * 查询所有学生信息
	 * @return
	 * @throws Exception
	 */
	public List<TStudent> findAllStu() throws Exception {
		List<TStudent> stuList;//写成两行
		String sql = "select * from tstudent";//写在openConnection之前
		this.openConnection();
		PreparedStatement ps = this.conn.prepareStatement(sql);
		ResultSet rs = ps.executeQuery();

		stuList = new ArrayList<TStudent>();//这样如果前面有错就不用产生内存分配
		while(rs.next()){
			TStudent ts = new TStudent();//new TStudent()是新建一个内存,这个不会被释放掉,只不过每次会建立对象引用
			ts.setSname(rs.getString("sname"));
			ts.setCno(rs.getString("cno"));
			ts.setSno(rs.getString("sno"));
			ts.setAddress(rs.getString("address"));
			ts.setSex(rs.getString("sex"));
			ts.setTel(rs.getString("tel"));
			ts.setBirthday(rs.getDate("birthday"));
			ts.setHeight(rs.getInt("height"));
			ts.setState(rs.getInt("state"));
			stuList.add(ts);//集合里面放的是引用,向集合中添加,就是复制对象地址,然后释放这个对象地址
		}
		rs.close();
		ps.close();

		return stuList;
	}

}

basedao

public class BaseDao {
	protected Connection conn;		

	public void openConnection() throws Exception{

		//通过反射技术,对oracel的驱动对象进行类的加载 (其实是在做类型检查)
		//在类的加载时,会调用OracleDriver中的静态代码块和静态变量初始化
		Class.forName("oracle.jdbc.driver.OracleDriver");  
		conn = DriverManager.getConnection("jdbc:oracle:thin:@10.0.19.252:1521:orcl","itxy","itxy");
	}

	public void closeConnection() {
		if(this.conn != null){
			try {
				this.conn.close();
			} catch (Exception e) {
				e.printStackTrace();
			}
		}
	}
}
时间: 2024-10-12 23:45:44

JDBC和异常总结及常见使用的相关文章

JDBC 数据库异常 Exception 关闭的(语句,连接,ResultSet)

如果在rs.next()之前关闭了Statement或PreparedStatement,会导致下面的异常: java.sql.SQLException: 关闭的语句: next 如果在rs.next()之前关闭了Connection,会导致下面的异常: java.sql.SQLException: 关闭的连接: next问题 如果在rs.next()之前关闭了ResultSet,会导致下面的异常: java.sql.SQLException: 关闭的 Resultset: next JDBC

JDBC的异常

以下内容引用自http://wiki.jikexueyuan.com/project/jdbc/exceptions.html: 异常处理可以允许处理一个异常情况,例如可控方式的程序定义错误. 当异常情况发生时,将抛出一个异常.抛出这个词意味着当前执行的程序停止,控制器被重定向到最近的适用的catch子句.如果没有适用的catch子句存在,那么程序执行被终止. JDBC的异常处理是非常类似于Java的异常处理,但对于JDBC,最常见的异常是java.sql.SQLException. 一.SQL

Java异常打印输出中常见方法的分析

Java异常是在Java应用中的警报器,在出现异常的情况下,可以帮助我们程序猿们快速定位问题的类型以及位置.但是一般在我们的项目中,由于经验阅历等多方面的原因,依然有若干的童鞋在代码中没有正确的使用异常打印方法,导致在项目的后台日志中,没有收到日志或者日志信息不完整等情况的发生,这些都给项目埋下了若干隐患.本文将深入分析在异常日志打印过程中的若干情况,并给出若干的使用建议. 1. Java异常Exception的结构分析 我们通常所说的Exception主要是继承于Throwable而来,可以参

JAVA中常见异常小结

1.java.lang.ArithmeticException 算术运算异常,例如除数为0,所以引发了算数异常 2.Java.lang.StringIndexOutOfBoundsException:  这是截取字符串substring()产生的下标越界异常.原因是可能是字符串为空,或长度不足1 3.Java.lang.NullPointerException空指针异常 出现该异常的原因在于某个引用为null,但却调用了它的某个方法,这时就会出现该异常 4.ClassCastException

Hbase delete遇到的常见异常: Exception in thread &quot;main&quot; java.lang.UnsupportedOperationException

hbase 执行批量删除时出现错误: Exception in thread "main" java.lang.UnsupportedOperationException at java.util.AbstractList.remove(AbstractList.java:161) at org.apache.hadoop.hbase.client.HTable.delete(HTable.java:852) 这种异常其实很常见,remove操作不支持,为什么会出现不支持的情况呢?检查

Java千百问_04异常处理(007)_常见的java异常有哪些(非运行时)

点击进入_更多_Java千百问 1.常见的java运行时异常有哪些 了解非运行时异常看这里:什么是java中的异常 常见的运行时异常看这里:常见的运行时异常有哪些 我们所说的常见异常是jdk或者其他常用第三方jar中的异常,出现频次很高的异常.常见的非运行时异常(即检查异常,checked exception)包括: 操作数据库异常:SQLException 输入输出异常:IOException 文件未找到异常:FileNotFoundException 反射操作异常:ReflectiveOpe

常见的几种异常类型-熟记

今天把几个常见的异常总结一下,希望自己能熟记,别忘记!!! 1.NullPointerException: 空指针异常.菜鸟编程经验发现这个异常是经常会发生的,属于运行时异常. 举例: public static void main(String[] args) {String str = null;//此处报空指针异常System.out.println(str.length());} 控制台输出的异常信息为: Exception in thread "main" java.lang

iOS开发中常见的一些异常

iOS开发中常见的异常包括以下几种NSInvalidArgumentExceptionNSRangeExceptionNSGenericExceptionNSInternallnconsistencyExceptionNSFileHandleOperationException NSInvalidArgumentException非法参数异常是objective-C代码最常出现的错误,所以平时写代码的时候,需要多加注意,加强对参数的检查,避免传入非法参数导致异常,其中尤以nil参数为甚. 1.集

浅谈java异常[Exception]

本文转自:focusJ 一. 异常的定义 在<java编程思想>中这样定义 异常:阻止当前方法或作用域继续执行的问题.虽然java中有异常处理机制,但是要明确一点,决不应该用"正常"的态度来看待异常.绝对一点说异常就是某种意义上的错误,就是问题,它可能会导致程序失败.之所以java要提出异常处理机制,就是要告诉开发人员,你的程序出现了不正常的情况,请注意. 记得当初学习java的时候,异常总是搞不太清楚,不知道这个异常是什么意思,为什么会有这个机制?但是随着知识的积累逐渐也