目的

简化代码,提高开发效率

设计模式

策略设计模式

代码

 #连接设置
driverClassName=com.mysql.jdbc.Driver
url=jdbc:mysql://localhost:3306/day17
username=root
password=sorry #<!-- 初始化连接 -->
initialSize=10 #最大连接数量
maxActive=50 #<!-- 最大空闲连接 -->
maxIdle=20 #<!-- 最小空闲连接 -->
minIdle=5 #<!-- 超时等待时间以毫秒为单位 6000毫秒/1000等于60秒 -->
maxWait=60000 #JDBC驱动建立连接时附带的连接属性属性的格式必须为这样:[属性名=property;]
#注意:"user" 与 "password" 两个属性会被明确地传递,因此这里不需要包含他们。
connectionProperties=useUnicode=true;characterEncoding=utf8 #指定由连接池所创建的连接的自动提交(auto-commit)状态。
defaultAutoCommit=true #driver default 指定由连接池所创建的连接的只读(read-only)状态。
#如果没有设置该值,则“setReadOnly”方法将不被调用。(某些驱动并不支持只读模式,如:Informix)
defaultReadOnly= #driver default 指定由连接池所创建的连接的事务级别(TransactionIsolation)。
#可用值为下列之一:(详情可见javadoc。)NONE,READ_UNCOMMITTED, READ_COMMITTED, REPEATABLE_READ, SERIALIZABLE
defaultTransactionIsolation=REPEATABLE_READ

dbcpconfig.properties

 import java.util.List;
import org.junit.Test;
import com.itheima.dbassist.BeanHandler;
import com.itheima.dbassist.BeanListHandler;
import com.itheima.dbassist.DBAssist;
import com.itheima.domain.User;
import com.itheima.util.DBCPUtil; public class UserDaoImpl {
private DBAssist da = new DBAssist(DBCPUtil.getDataSource());
//SQL和参数
@Test
public void add(){
da.update("insert into user values(?,?,?,?)", "aa","wf","123","非同寻常");
}
@Test
public void update(){
da.update("update user set password=? where id=?", "12345","aa");
}
@Test
public void delete(){
da.update("delete from user where id=?", "aa");
}
@Test
public void query1(){
User user = (User)da.query("select * from user where id=?", new BeanHandler(User.class), "a5cc6e18-f3b8-44a6-bcdd-c6476f1edb87");
System.out.println(user);
}
@Test
public void query2(){
List<User> users = (List<User>)da.query("select * from user", new BeanListHandler(User.class));
for(User user:users)
System.out.println(user);
}
}

UserDaoImpl

 import java.lang.reflect.Field;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
import java.util.ArrayList;
import java.util.List;
/**
* 适合有多条结果记录的数据封装
* 返回的是一个List
*
*/
public class BeanListHandler implements ResultSetHandler {
private Class clazz;
public BeanListHandler(Class clazz){
this.clazz = clazz;
}
public Object handle(ResultSet rs) {
try {
List list = new ArrayList();
while(rs.next()){
Object bean = clazz.newInstance();
//封装数据:书写JavaBean的前提,类中的字段名或属性名与数据库表的字段名保持一致
ResultSetMetaData rsmd = rs.getMetaData();
int columnCount = rsmd.getColumnCount();
for(int i=0;i<columnCount;i++){
String columnName = rsmd.getColumnName(i+1);//与JavaBean的字段名一致
Object columnValue = rs.getObject(columnName);//列值 //得到JavaBean的对应字段
Field field = clazz.getDeclaredField(columnName);
field.setAccessible(true);//强暴它 有可能是私有的
field.set(bean, columnValue);
}
list.add(bean); }
return list;
} catch (Exception e) {
throw new RuntimeException("封装数据失败");
}
}
}

BeanListHandler

 import java.sql.Connection;
import java.sql.ParameterMetaData;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement; import javax.sql.DataSource; import com.itheima.util.DBCPUtil; public class DBAssist {
private DataSource dataSource;
public DBAssist(DataSource dataSource){
this.dataSource = dataSource;
}
/*
* 能够执行DML语句:INSERT UPDATE DELETE
*/
public void update(String sql,Object...params){
Connection conn = null;
PreparedStatement stmt = null;
ResultSet rs = null;
try{
conn = dataSource.getConnection();//具体的数据源无关
stmt = conn.prepareStatement(sql);
//看sql中的占位符的个数:参数元信息的获取
ParameterMetaData pmd = stmt.getParameterMetaData();
int paramCount = pmd.getParameterCount();
//设置参数:略
if(paramCount>0){
//判断参数占位符的个数和params的个数是否一致
if(params==null||params.length!=paramCount){
throw new RuntimeException("参数个数不匹配");
}
//设置SQL中的参数占位符的值
for(int i=0;i<paramCount;i++){
stmt.setObject(i+1, params[i]);
}
}
stmt.executeUpdate();
}catch(Exception e){
throw new RuntimeException(e);
}finally{
release(rs, stmt, conn);
}
}
/**
* 执行查询
* @return 封装了数据的对象
*/
public Object query(String sql,ResultSetHandler handler,Object...params){
Connection conn = null;
PreparedStatement stmt = null;
ResultSet rs = null;
try{
conn = dataSource.getConnection();
stmt = conn.prepareStatement(sql);
//看sql中的占位符的个数:参数元信息的获取
ParameterMetaData pmd = stmt.getParameterMetaData();
int paramCount = pmd.getParameterCount();
//设置参数:略
if(paramCount>0){
//判断参数占位符的个数和params的个数是否一致
if(params==null||params.length!=paramCount){
throw new RuntimeException("参数个数不匹配");
}
//设置SQL中的参数占位符的值
for(int i=0;i<paramCount;i++){
stmt.setObject(i+1, params[i]);
}
}
rs = stmt.executeQuery();//如何封装呢:
//有结果集:不知道有什么字段和值
//不知道封装成什么对象:谁用谁知道 //策略:有数据----->有目标
return handler.handle(rs);
}catch(Exception e){
throw new RuntimeException(e);
}finally{
release(rs, stmt, conn);
}
}
private void release(ResultSet rs,Statement stmt,Connection conn){
if(rs!=null){
try {
rs.close();
} catch (SQLException e) {
e.printStackTrace();
}
rs = null;
}
if(stmt!=null){
try {
stmt.close();
} catch (SQLException e) {
e.printStackTrace();
}
stmt = null;
}
if(conn!=null){
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
conn = null;
}
}
}

DBAssist

 package com.itheima.dbassist;

 import java.sql.ResultSet;
//抽象策略
public interface ResultSetHandler {
/**
*把结果集中的数据封装到对象中
* @param rs
* @return
*/
Object handle(ResultSet rs);
}

ResultSetHandler

 import java.lang.reflect.Field;
import java.sql.ResultSet;
import java.sql.ResultSetMetaData;
//策略的具体实现
/**
* 专门用于封装结果中只有一条的记录的情况
* 返回值:封装好的Java对象
*
*/
public class BeanHandler implements ResultSetHandler {
private Class clazz;
public BeanHandler(Class clazz){
this.clazz = clazz;
}
public Object handle(ResultSet rs) {
try {
if(rs.next()){
Object bean = clazz.newInstance();
//封装数据:书写JavaBean的前提,类中的字段名或属性名与数据库表的字段名保持一致
ResultSetMetaData rsmd = rs.getMetaData();
int columnCount = rsmd.getColumnCount();
for(int i=0;i<columnCount;i++){
String columnName = rsmd.getColumnName(i+1);//与JavaBean的字段名一致
Object columnValue = rs.getObject(columnName);//列值 //得到JavaBean的对应字段
Field field = clazz.getDeclaredField(columnName);
field.setAccessible(true);//强暴它 有可能是私有的
field.set(bean, columnValue);
} return bean;
}
return null;
} catch (Exception e) {
throw new RuntimeException("封装数据失败");
}
} }

BeanHandler

 public class User {
private String id;
private String username;
private String password;
private String nick;
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
public String getNick() {
return nick;
}
public void setNick(String nick) {
this.nick = nick;
}
@Override
public String toString() {
return "User [id=" + id + ", username=" + username + ", password="
+ password + ", nick=" + nick + "]";
} }

User

 import java.io.InputStream;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Properties; import javax.sql.DataSource; import org.apache.commons.dbcp.BasicDataSourceFactory; public class DBCPUtil {
private static DataSource dataSource;
static{
try {
InputStream in = DBCPUtil.class.getClassLoader().getResourceAsStream("dbcpconfig.properties");
Properties props = new Properties();
props.load(in);
dataSource = BasicDataSourceFactory.createDataSource(props);
} catch (Exception e) {
throw new ExceptionInInitializerError("初始化数据源失败");
}
}
public static Connection getConnection(){
try {
return dataSource.getConnection();
} catch (SQLException e) {
throw new RuntimeException("获取数据库连接失败");
}
}
public static DataSource getDataSource(){
return dataSource;
} }

DBCPUtil

编写自己的JDBC框架的更多相关文章

  1. 【总结】编写自己的JDBC框架

    一.数据库连接池: 在一般用JDBC 进行连接数据库进行CRUD操作时,每一次都会: 通过:java.sql.Connection conn = DriverManager.getConnection ...

  2. javaweb学习总结(四十)——编写自己的JDBC框架

    一.元数据介绍 元数据指的是"数据库"."表"."列"的定义信息. 1.1.DataBaseMetaData元数据 Connection.g ...

  3. 编写自定义的JDBC框架与策略模式

    本篇根据上一篇利用数据库的几种元数据来仿造Apache公司的开源DbUtils工具类集合来编写自己的JDBC框架.也就是说在本篇中很大程度上的代码都和DbUtils中相似,学完本篇后即更容易了解DbU ...

  4. javaweb总结(四十)——编写自己的JDBC框架

    一.元数据介绍 元数据指的是"数据库"."表"."列"的定义信息. 1.1.DataBaseMetaData元数据 Connection.g ...

  5. 编写自己的JDBC框架(转)

    一.元数据介绍 元数据指的是"数据库"."表"."列"的定义信息. 1.1.DataBaseMetaData元数据 Connection.g ...

  6. java web学习总结(二十三) -------------------编写自己的JDBC框架

    一.元数据介绍 元数据指的是"数据库"."表"."列"的定义信息. 1.1.DataBaseMetaData元数据 Connection.g ...

  7. JDBC 学习复习10 编写自己的JDBC框架

    首先万分感谢狼哥 孤傲苍狼 博客,整个jdbc学习的博客资料 链接为http://www.cnblogs.com/xdp-gacl/p/4006830.html 详细代码见狼哥博客,列出我学习过程中遇 ...

  8. JDBC框架

    一.元数据介绍 元数据指的是"数据库"."表"."列"的定义信息. 1.1.DataBaseMetaData元数据 Connection.g ...

  9. Spring的JDBC框架

    转自: http://www.cnblogs.com/windlaughing/p/3287750.html Spring JDBC提供了一套JDBC抽象框架,用于简化JDBC开发. Spring主要 ...

随机推荐

  1. 对于使用secureFX上传文件到centos7 的时候,以及不同的用户解压文件,对于文件操作权限的实验

    本以为以一个用户胡如root登录了SecureFx,之后选择了root的家目录下的一个software目录,之后上传 以root用户远程登录LINUX系统 查看文件 之后再验证普通用户zhaijh登录 ...

  2. Win10-IIS注册asp 此操作系统版本不支持此选项 错误解决方法

    现象再现: 今日在Win10上面ASP.NET网站突然不能跑了, 过程再现: 根据资料提示重新注册ASPNET_IIS.exe -i 直接提示: C:\WINDOWS\system32>c:\w ...

  3. XMOS发布集单片机,AI,FPGA,DSP于一身的跨界处理器完全体xcore.ai,致力于AIOT,售价1美元起步

    说明:XMOS这次致力于打造全新的,颠覆性的嵌入式平台,简化开发人员要学一堆东西才能开发一款高性能AIOT产品的痛点. XCORE.AI集单片机,AI,FPGA,DSP于一身,嵌入式软件开发人员可以灵 ...

  4. 方便的 IcoMoon 图标字体

    官网地址:https://icomoon.io/app/#/select 已发现的方便之处: 1.官网已提供大量常用图标字体: 2.可通过 svg 将其转换为 图标字体: 3.不仅可转换,还可自定义编 ...

  5. kindeditor文件上传设置文件说明为上传文件名(JSP版)

    编辑器换成kindeditor时发现文件上传后,直接点确定,<a>便签中的内容显示的是文件路径,不是我想要的文件名,我试了百度上的一些设置方法都不行的,百度上大部分都是修改pugins/i ...

  6. STM32F103之GPIO学习记录

    9 GPIO:通用I/O口 AFIO:可供选择的I/O口 9.1 GPIO功能描述 每一个通用的I/O口都有: 两个32位的配置寄存器(配置寄存器低和配置寄存器高): 两个32位的数据寄存器(输入数据 ...

  7. SmartRobotControlPlateform——智能机器人控制平台

    具体成果参考github项目:https://github.com/ecjtuseclab/SmartRobotControlPlateform 这里我使用的镜像是:2018-11-13-raspbi ...

  8. Java面向对象编程 -5

    代码块 在程序之中使用"{}"定义的结构就称为代码块,而后根据代码块出现的位置以及定义的关键字的不同, 代码块可以分为 普通代码块 构造代码块 静态代码块 同步代码块 其中同步代码 ...

  9. idea 快捷使用(三)中断Debug的使用

    想要在Debug的时候,中断请求,不要再走剩余的流程了? 不需要关闭服务重新启动程序,可以通过Force Return,即强制返回来避免后续的流程. 点击Force Return,弹出Return V ...

  10. 使用Eclipse工具开发Servlet(新建web项目->创建Servlet->部署和访问Servlet)

    在Eclipse工具栏中的[File]->[New]->[Other],打开如下菜单栏,选择Dynamic Web Project 点击下一步,如下图所示: 这里Dynamic web m ...