Java学习总结(十九)——JDBC操作数据库,预编译的使用,事务,常见的连接池

一.JDBC操作数据库

1. JDBC(Java DataBase Connection,java数据库连接),由一些接口和类构成的API。

图示:

 


2. JDBC操作数据库的步骤:

(1)注册驱动

(2)建立连接(Connectoin)

(3)创建执行SQL的语句(Statement)

(4)执行SQL语句(通过StatementPreparedStatement

(5)处理执行结果(resultSet

(6)释放资源

3. 建立连接:

(1)Connection conn=DriverManager.getConnection(url,user,password);

(2)Url格式:Jdbc:子协议://主机名:端口/数据库名? 属性名=属性值&......

3User(用户名),password(密码)可以用,“属性名=属性值”方式告诉数据库

4)其他参数如:

useUnicode=true&characterEncoding=GBK

4. 执行sql时:

(1)增,删,改用executeUpdate()方法

(2)查询时使用executeQuery()方法

1(向数据库中添加元素):

(1)创建工程,引入数据库连接jar包,并建立环境连接;

 

(2)编写代码(往):

package org.jdbc.insert;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.sql.Statement;

public class InsertDemo {

	public static void main(String[] args) {
		Connection conn = null;
		Statement stat = null;
		try {
			// 1.建立驱动,加载驱动程序
			Class.forName("com.mysql.jdbc.Driver");
			// 2.建立连接,与数据库进行连接
			conn = DriverManager.getConnection(
					"jdbc:mysql://localhost:3306/mydb?characterEncoding=utf8",
					"root", "qitao1996");
			// 3.编写待执行的sql语句,以及sql语句执行对象
			String sql = "insert into students(id,name,age,score) values(15,'丁明君',22,93.2),(16,'小昭',18,94.7)";
			stat = conn.createStatement();
			// 4.执行sql语句,并返回影响数据库表中的行数
			int count = stat.executeUpdate(sql);
			// 5.处理运行结果
			if (count > 0) {
				System.out.println("数据添加成功,影响了表中" + count + "行数据!!!!!");
			}
		} catch (Exception e) {
			e.printStackTrace();
		} finally {
			try {
				// 6.释放资源
				conn.close();
				stat.close();
			} catch (SQLException e) {
				e.printStackTrace();
			}
		}
	}

}

 

 

3运行结果:

 

2(查询数据库中元素,并打印到控制台):

1)编写代码:

package org.jdbc.select;

import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;

public class QueryDemo {

	public static void main(String[] args) {
		Connection conn=null;
		Statement stat=null;
		ResultSet rs=null;
		try {
			Class.forName("com.mysql.jdbc.Driver");//建立驱动
			//建立连接
			conn=DriverManager.getConnection("jdbc:mysql://localhost:3306/mydb?user=root&password=qitao1996");
			String sql="select * from students";//编写sql语句
			stat=conn.createStatement();//创建执行
			rs= stat.executeQuery(sql);//执行sql语句,并返回查询到的结果集
			System.out.println("获取到的学生信息为:");
			System.out.println("学号\t姓名\t年龄\t成绩");
			//遍厉获取查询到的结果集
			while(rs.next()){
				int id=rs.getInt("id");
				String name=rs.getString("name");
				int age=rs.getInt("age");
				double score=rs.getDouble("score");
				System.out.println(id+"\t"+name+"\t"+age+"\t"+score);
			}
		} catch (Exception e) {
			e.printStackTrace();
		}finally{
			try {
				conn.close();
				stat.close();
				rs.close();//释放资源
			} catch (SQLException e) {
				e.printStackTrace();
			}
		}
	}

}

 

2)运行结果:

 

5. 批处理:

1)应用addBatch()方法添加批处理语句

2)使用executeBatch方法执行批处理

3(分别编写增,删,改语句各一条一次执行):

(1)编写代码:

package org.jdbc.batch;
 
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.SQLException;
import java.sql.Statement;
 
public class BatchDemo {
 
public static void main(String[] args) {
Connection conn=null;
Statement stat=null;
try {
Class.forName("com.mysql.jdbc.Driver");//建立驱动
//建立连接
conn=DriverManager.getConnection("jdbc:mysql://localhost:3306/mydb","root","qitao1996");
stat=conn.createStatement();
//下面添加批处理语句
stat.addBatch("insert into students(name,age,score) values('王昭君',21,99.2 )");
stat.addBatch("delete from students where id=16");
stat.addBatch("update students set id=11 where id=15");
int[] array=stat.executeBatch();//执行批处理命令
int i=1;
    for(int count:array){
System.out.println("第"+i+"条语句执行影响行数为"+count);
i++;
}
} catch (Exception e) {
e.printStackTrace();
}finally{
try {
conn.close();
stat.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
 
}


 

(2)运行结果:

 

二.PreparedStatement的使用

1. preparedStatement是Statement的子接口,属于预处理操作

2. 获取PreparedStatement的方法:

使用Connection对象的PreparedStatement preparedstatement(String sql)

3. 使用PreparedStatement的好处:

(1)对于相同结构的SQL,可以提高执行效率:

@@1.在创建PreparedStatement对象时就指定了sql语句,该语句将立即被发送给DBMS进行编译

@@2.预编译的语句被存储在DBMS的缓存中,下次执行相同的SQL语句时,则可以从缓存中取出来。

(2)可以有效地预防SQL注入:

在使用参数化查询的情况下,数据库系统(DBMS)不会将参数的内容视为SQL指令的一部分来处理,而是在数据库完成SQL指令的编译后,才套用参数运行,即使参数中含有恶意的指令,也不会被数据库所运行

根据以前所学,我们先来编写一个获取JDBC连接的对象的工具类方便后续代码使用:

(1)首先在src目录下新建一个properties属性文件

 

内容:

 

driverclass=com.mysql.jdbc.Driver
user=root
password=qitao1996
url=jdbc:mysql://127.0.0.1:3306/boke18


(2)编写工具类代码

package org.jdbc.util;
 
import java.io.File;
import java.io.FileInputStream;
import java.io.InputStream;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Properties;
 
//操作数据库的工具类
public class DBUtil {
//私有化构造方法
private DBUtil(){
}
private static String url=null;
private static String user=null;
private static String password=null;
static{
try {
Class.forName("com.mysql.jdbc.Driver");
Properties pro=new Properties();
pro.load(new FileInputStream("src/jdbc.properties"));
url=pro.getProperty("url");
user=pro.getProperty("user");
password=pro.getProperty("password");
} catch (Exception e) {
e.printStackTrace();
}
}
//读取外部属性文件获取连接对象,需手动输入url
public static Connection getConnection1(String url){
Properties pro=new Properties();
Connection conn=null;
InputStream input=null;
try {
input=new FileInputStream("E:"+File.separator+"JDBC.properties");
pro.load(input);
conn=DriverManager.getConnection(url,pro);
} catch (Exception e) {
e.printStackTrace();
}
return conn;
}
//读取工程下的配置文件,获取连接对象参数,不需手动输入url
public static Connection getConnection2() throws SQLException{
Connection conn=DriverManager.getConnection(url,user,password);
return conn;
}
//释放全部资源
public static void closeAll(Connection conn,Statement stat,ResultSet rs) throws SQLException{
if(conn!=null){
conn.close();
}
if(stat!=null){
stat.close();
}
if(rs!=null){
rs.close();
}
} 
//释放所用资源
public static void closePart(Connection conn,Statement stat) throws SQLException{
if(conn!=null){
conn.close();
}
if(stat!=null){
stat.close();
}
} 
}


 

 

1(根据拼串来模拟SQL注入):

(1)利用上述工具类编写代码:

package org.jdbc.inject;
 
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
 
import org.jdbc.util.DBUtil;
 
public class SqlInjectDemo {
 
public static void main(String[] args) {
Statement stat=null;
ResultSet rs=null;
Connection conn=null;
try {
conn=DBUtil.getConnection2();
stat=conn.createStatement();
String username="西施";
String password="xyz' or '1=1";
String sql="select * from user where username='"+username+"' and password='"+password+"'";
System.out.println(sql);
rs=stat.executeQuery(sql);
if(rs.next()){
System.out.println("恭喜你登录,成功");
}else{
System.out.println("很遗憾,你的用户名或密码输入错误,登录失败");
}
} catch (Exception e) {
e.printStackTrace();
}finally{
try {
DBUtil.closeAll(conn, stat, rs);
} catch (SQLException e) {
e.printStackTrace();
}
}
}
 
}


 

 

(2)运行结果:

 

我们来查询user表中元素,看看是否出现了sql注入现象

 

对比可以知道,在这个例子中就出现了SQL注入,导致我们程序的不安全性

2(现在我们来使用预编译的方法防止SQL的注入):

1)编写代码:

package org.jdbc.inject;
 
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
 
import org.jdbc.util.DBUtil;
 
public class StopInject {
 
public static void main(String[] args) {
PreparedStatement ps=null;
ResultSet rs=null;
Connection conn=null; 
String sql="select * from user where username=? and password=? ";//编写预编译sql
BufferedReader br=new BufferedReader(new InputStreamReader(System.in));
try {
conn=DBUtil.getConnection2();
ps=conn.prepareStatement(sql);
System.out.print("请输入用户名:");
String username=br.readLine();
System.out.print("请输入密码:");
String password=br.readLine();
ps.setString(1, username);
ps.setString(2, password);
rs=ps.executeQuery();//执行sql语句
if(rs.next()){
System.out.println("恭喜你,登录成功....");
}else{
System.out.println("你的用户名或密码输入错误,登录失败....");
} 
} catch (Exception e) {
e.printStackTrace();
}finally{
try {
DBUtil.closeAll(conn,ps, rs);
} catch (SQLException e) {
e.printStackTrace();
}
}
}
 
}


2)运行结果:

当用户名密码都正确时:

 

利用拼串,鼓故意写错密码时:

 

由此我们清楚地发现预编译有效地防止了SQL注入现象

3(使用预编译向表中添加和查询元素):

(1)编写代码:

package org.jdbc.inject;
 
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
 
import org.jdbc.util.DBUtil;
 
public class InsertDemo {
// 获取类中可以共用的对象
private static Connection conn = null;
private static PreparedStatement ps = null;
private static ResultSet rs = null;
// 代码运行时即开始连接数据库
static {
try {
conn = DBUtil.getConnection2();
} catch (SQLException e) {
e.printStackTrace();
}
}
 
// 添加元素
public static void main(String[] args) {
String sql = "insert into user(username,password) values(?,?)";
try {
// 将SQL发送到DBMS中,进行预编译,将预编译好的SQL存储于DBMS的缓冲区中
ps = conn.prepareStatement(sql);
for (int i = 1; i <= 10; i++) {
ps.setString(1, "貂蝉" + i);
ps.setString(2, "64251" + i);
ps.executeUpdate();
}
System.out.println("数据库中批量添加元素成功...");
System.out.println("查看表中元素");
selectAll();// 调用查询方法
} catch (SQLException e) {
e.printStackTrace();
} finally {
try {
DBUtil.closePart(conn, ps);// 释放资源
} catch (SQLException e) {
e.printStackTrace();
}
}
}
 
// 查询元素
public static void selectAll() {
String sql = "select * from user";
try {
ps = conn.prepareStatement(sql);
rs = ps.executeQuery();// 执行sql
System.out.println("查询user表得:");
System.out.println("编号\t用户名\t密码");
// 遍厉打印元素
while (rs.next()) {
int id = rs.getInt("id");
String username = rs.getString("username");
String password = rs.getString("password");
System.out.println(id + "\t" + username + "\t" + password);
}
} catch (SQLException e) {
e.printStackTrace();
} finally {
try {
DBUtil.closeAll(conn, ps, rs);
} catch (SQLException e) {
e.printStackTrace();
}
}
}
 
}


 

 

(2)运行结果:

 

4(我们将查询到的数据封装到JavaBean中):

(1)首先编写JavaBean,用来封装数据

package org.jdbc.bean;
 
public class User {
private int id;
private String username;
private String password;
 
public User(){
}
 
public User(int id, String username, String password) {
this.id = id;
this.username = username;
this.password = password;
}
 
public int getId() {
return id;
}
 
public void setId(int 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;
}
 
@Override
public String toString() {
return "User [id=" + id + ", username=" + username + ", password="
+ password + "]";
}
 
}


 

 

(2)我们将例3中查询方法稍作修改,将元素封装到List集合中:

List<User> list = new ArrayList<User>();
String sql = "select * from user";
try {
ps = conn.prepareStatement(sql);
rs = ps.executeQuery();// 执行sql
System.out.println("查询user表得:");
System.out.println("编号\t用户名\t密码");
// 遍厉打印元素
User user = new User();
while (rs.next()) {
int id = rs.getInt("id");
String username = rs.getString("username");
String password = rs.getString("password");
System.out.println(id + "\t" + username + "\t" + password);
user = new User(id, username, password);
list.add(user);// 将对象添加到集合中
}
for (User user1 : list) {
System.out.println(user1);


}

 

(3)运行结果:

 

5(将Java中的对象添加到数据库中去):

(1)编写代码(以上述代码为基础,添加一个添加对象的方法):

// 将JavaBean中的对象添加到数据库中
public static void userInsert() {
List<User> list = new ArrayList<User>();
User user = new User();
for (int j = 1; j <= 5; j++) {
user = new User("武则天" + j, "75332" + j);
list.add(user);
}
String sql = "insert into user(username,password) values(?,?)";
int count = 0;
try {
ps = conn.prepareStatement(sql);
for (User user2 : list) {
ps.setString(1, user2.getUsername());
ps.setString(2, user2.getPassword());
count = ps.executeUpdate();
}
if (count > 0) {
System.out.println("添加元素成功..");
} else {
System.out.println("添加元素失败..");
}
} catch (SQLException e) {
e.printStackTrace();
} // 查询完毕后,由查询方法释放资源
}


 

(2)运行结果:

 

三.事务

1. 概念:数据库事务(Database Transaction),是指作为单个逻辑工作单元执行的那一系列操作,要么全部成功,要么全部失败

2. 事务的四个特性:

(1)原子性:原子性是指事务是一个不可分割的单位,事务中的操作要么都发生,要么都失败

(2)一致性:事务必须使数据库从一个一致性的状态变换到另一个一致性的状态

(3)隔离性:事务的隔离级别是指一个事务的执行不被其他事务所干扰,即一个事务内部的操作及使用的数据对并发的 其他事务是隔离的,并发执行的各个事务之间不能互相干扰

(4)持久性:持久性是指一个事务一旦被提交,它对数据库中的数据改变就是永久性的,接下来的其他操作和数据库故障不应该对其有任何的影响

3. 事务的隔离级别

前提概念:

(1)脏读(dirty read):一个事务读取到了另一个事务未提交的数据(脏数据)的现象

(2)不可重复读:一个事务两次读取到的数据不一致的现象

(3)幻读:一个事务在读取数据时,另一个事务添加了数据记录,则第一个事务读取到了新添加的数据(与第一次读取到的数据比较)

级别分类:

(1)读未提交级别(read uncommitted):读取到了另一个事务还未提交的数据,可能发生脏读,不可重复读,幻读。

(2)读提交级别(read committed):只能读取其他事务已经提交的数据,可能会发生不可重复读,幻读

(3)可重复提交级别(repeatable read,MySQL默认隔离级别):在一个事务中可以重复读取相同的数据在InnoDB数据库存储引擎(此存储引擎支持事务)中,已经解决了幻读问题。

(4)串行化级别(serialzable): 最安全,但并发效率低。

4. 隔离级别多线程并发读取数据时的正确性

隔离级别 

脏读 

不可重复读 

幻读 

读未提交(Read uncommitted

V

V

V

读已提交(Read committed

x

V

V

可重复读(Repeatable read

x

x

V

可串行化(Serializable 

x

x

x

V:可能出现,X:不会出现

5. Java对事务的支持

(1)当一个连接对象被创建时,默认情况下是自动提交事务:每次执行一个 SQL 语句时,如 果执行成功,就会向数据库自动提交,而不能回滚

     为了让多个 SQL 语句作为一个事务执行:

(2)调用 Connection 对象的 setAutoCommit(false); 以取消自动提交事务

(3)在所有的 SQL 语句都成功执行后,调用 commit(); 方法提交事务

(4)在出现异常时,调用 rollback(); 方法回滚事务

(5)若此时 Connection 没有被关闭, 则需要恢复其自动提交状态

1(模拟银行账户对事物进行深入理解,具有转账,查询功能):

(1)编写代码:

package org.jdbc.transcation;
 
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Scanner;
 
import org.jdbc.util.DBUtil;
 
public class AccountDemo {
// 主方法控制运行方向
public static void main(String[] args) {
BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
Scanner scan = new Scanner(System.in);
while (true) {
System.out.print("请输入你的选择(1 转账\t2 查询\t3退出):");
int chioce;
try {
chioce = scan.nextInt();
switch (chioce) {
case 1:
System.out.print("请输入转出账户的姓名:");
String fromName = br.readLine();
System.out.print("请输入转入账户姓名:");
String toName = br.readLine();
System.out.print("请输入转账金额:");
int money = scan.nextInt();
boolean flag = transFerMoney(fromName, toName, money);
if (flag) {
System.out.println("转账成功");
} else {
System.out.println("sorry,ATM发生故障,转账失败!");
}
break;
case 2:
System.out.print("请选择 (1:查询全部账户\t2:个人账户):");
int chioce1 = scan.nextInt();
switch (chioce1) {
case 1:
selectAll();
break;
case 2:
System.out.print("请输入查询账户姓名:");
String balName = br.readLine();
selectPart(balName);
break;
}
break;
case 3:
System.out.println("谢谢你的光临,再见!!");
System.exit(0);
}
} catch (IOException e) {
e.printStackTrace();
}
}
 
}
 
// 转钱方法
public static boolean transFerMoney(String fromName, String toName,
int money) {
boolean flag = false;
PreparedStatement ps = null;
Connection conn = null;
try {
conn = DBUtil.getConnection2();
conn.setAutoCommit(false);// 取消自动提交
String sql1 = "update account set balance=balance-? where name=?";
String sql2 = "update account set balance=balance+? where name=?";
ps = conn.prepareStatement(sql1);
ps.setInt(1, money);
ps.setString(2, fromName);// 转出
ps.executeUpdate();
ps.close();
 
ps = conn.prepareStatement(sql2);
ps.setInt(1, money);
ps.setString(2, toName);// 转入
ps.executeUpdate();
conn.commit();// 提交事务
flag = true;
} catch (SQLException e) {
e.printStackTrace();
} finally {
try {
DBUtil.closePart(conn, ps);
} catch (SQLException e) {
e.printStackTrace();
}
}
return flag;
 
}
 
// 全部账户查询方法
public static void selectAll() {
PreparedStatement ps = null;
Connection conn = null;
ResultSet rs = null;
try {
conn = DBUtil.getConnection2();// 建立连接
String sql = "select * from account";
ps = conn.prepareStatement(sql);
rs = ps.executeQuery();
System.out.println("全部账户查询结果为:");
System.out.println("编号\t姓名\t账户余额");
while (rs.next()) {
int id = rs.getInt("id");
String name = rs.getString("name");
int balance = rs.getInt("balance");
System.out.println(id + "\t" + name + "\t" + balance);
}
} catch (SQLException e) {
e.printStackTrace();
} finally {
try {
DBUtil.closeAll(conn, ps, rs);
} catch (SQLException e) {
e.printStackTrace();
}
}
}
 
// 查询单人账户
public static void selectPart(String balName) {
PreparedStatement ps = null;
Connection conn = null;
ResultSet rs = null;
try {
conn = DBUtil.getConnection2();// 建立连接
String sql3 = "select * from account where name=?";
ps = conn.prepareStatement(sql3);
ps.setString(1, balName);
rs = ps.executeQuery();
System.out.println(balName + "账户查询结果为:");
System.out.println("编号\t姓名\t账户余额");
while (rs.next()) {
int id = rs.getInt("id");
String name = rs.getString("name");
int balance = rs.getInt("balance");
System.out.println(id + "\t" + name + "\t" + balance);
}
} catch (SQLException e) {
e.printStackTrace();
} finally {
try {
DBUtil.closeAll(conn, ps, rs);
} catch (SQLException e) {
e.printStackTrace();
}
}
}
 
}


 

 

(2)运行结果:

请输入你的选择(1 转账 2 查询 3退出):2

请选择 (1:查询全部账户 2:个人账户):1

全部账户查询结果为:

编号 姓名 账户余额

1 项羽 35000000

2 刘邦 20000000

3 李世民 50000000

4 赵匡胤 24000000

请输入你的选择(1 转账 2 查询 3退出):1

请输入转出账户姓名:项羽

请输入转入账户姓名:刘邦

请输入转账金额:3000

转账成功

请输入你的选择(1 转账 2 查询 3退出):2

请选择 (1:查询全部账户 2:个人账户):2

请输入查询账户姓名:刘邦

刘邦账户查询结果为:

编号 姓名 账户余额

2 刘邦 20003000

请输入你的选择(1 转账 2 查询 3退出):1

请输入转出账户姓名:项羽

请输入转入账户姓名:李世民

请输入转账金额:3000

转账成功

请输入你的选择(1 转账 2 查询 3退出):2

请选择 (1:查询全部账户 2:个人账户):1

全部账户查询结果为:

编号 姓名 账户余额

1 项羽 34994000

2 刘邦 20003000

3 李世民 50003000

4 赵匡胤 24000000

请输入你的选择(1 转账 2 查询 3退出):3

谢谢你的光临,再见!!

 

四.常见的数据库连接池

1.连接池:存储,并高效管理数据库连接对象的容器连接池,一般用于短暂的频繁的去建立链接,去操作数据库,比较节省资源,我们根据数据库建立一次链接,底层来说还是比较耗费资源的

2.DBCP的使用:

1)导入DBCP的两个jar包,以及数据库驱动jar包;

2)编码:

方式一(硬编码):

package org.jdbc.dbcpdemo;
 
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
 
import org.apache.commons.dbcp.BasicDataSource;
 
public class DBCPDemo1 {
 
public static void main(String[] args) throws SQLException {
BasicDataSource ds = new BasicDataSource();
// 1.设置参数
ds.setDriverClassName("com.mysql.jdbc.Driver");
ds.setUrl("jdbc:mysql://localhost:3306/boke18");
ds.setUsername("root");
ds.setPassword("qitao1996");
// 2.获取连接对象
Connection conn = ds.getConnection();
String sql = "insert into user(username,password) values(?,?)";
PreparedStatement ps = conn.prepareStatement(sql);
ps.setString(1, "平昭阳公主");
ps.setString(2, "987654");
int count = 0;
count = ps.executeUpdate();
if (count != 0) {
System.out.println("添加成功..");
} else {
System.out.println("添加失败..");
}
conn.close();
ps.close();
 
}
 
}


 

运行结果:

 

方式二(配置文件的方式):

加入配置文件:dbcp.properties

代码:

package org.jdbc.dbcpdemo;
 
import java.io.FileInputStream;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.util.Properties;
import javax.sql.DataSource;
import org.apache.commons.dbcp.BasicDataSourceFactory;
 
public class DBCPDemo2 {
 
public static void main(String[] args) throws Exception {
//用属性集合读取属性文件
Properties pro=new Properties();
pro.load(new FileInputStream("src/dbcp.properties"));
//传入属性集合
@SuppressWarnings("static-access")
DataSource ds=new BasicDataSourceFactory().createDataSource(pro);
Connection conn=ds.getConnection();
String sql = "insert into user(username,password) values(?,?)";
PreparedStatement ps = conn.prepareStatement(sql);
ps.setString(1, "窦漪房");
ps.setString(2, "789654");
int count = 0;
count = ps.executeUpdate();
if (count != 0) {
System.out.println("添加成功..");
} else {
System.out.println("添加失败..");
}
conn.close();
ps.close();
}
 
}


 

 

运行结果:

 

3.c3p0的使用:

1)导入jar

编码方式一(硬编码):

核心代码:

  

ComboPooledDataSource ds = new ComboPooledDataSource();
        //设置参数
        ds.setDriverClass("com.mysql.jdbc.Driver");
        ds.setJdbcUrl("jdbc:mysql://127.0.0.1:3306/mydb");
        ds.setUser("root");
        ds.setPassword("123456");
        //获取链接对象
        Connection conn = ds.getConnection();
        String sql = "insert into users values(?,?)";
        PreparedStatement statement = conn.prepareStatement(sql);
        statement.setString(1, "找六2");
        statement.setString(2, "654321");
        statement.executeUpdate();
        conn.close();
        ds.close();


 

编码方式二(读取配置文件):

package org.jdbc.c3p0demo;
 
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
 
import com.mchange.v2.c3p0.ComboPooledDataSource;
 
public class C3P0Demo {
 
public static void main(String[] args) throws SQLException {
ComboPooledDataSource ds=new ComboPooledDataSource("myoracle");
Connection conn=ds.getConnection();
String sql = "insert into user(username,password) values(?,?)";
PreparedStatement ps=conn.prepareStatement(sql);
ps.setString(1, "梁红玉");
ps.setString(2, "678954");
int count=0;
count= ps.executeUpdate();
if(count!=0){
System.out.println("添加成功..");
}else{
System.out.println("添加失败..");
}
ps.close();
conn.close();
}
}


 

运行结果:

 

析:

 

 

 

 

 

4. DButils的使用:

(1)代码:

 

package org.jdbc.dbutils;
 
import java.sql.SQLException;
import java.util.List;
import org.apache.commons.dbutils.QueryRunner;
import org.apache.commons.dbutils.handlers.BeanListHandler;
import org.jdbc.bean.User;
import com.mchange.v2.c3p0.ComboPooledDataSource;
 
public class DButilsDemo {
 
public static void main(String[] args) throws SQLException {
// dbutils 封装了操作对象 配合C3P0一起使用
ComboPooledDataSource ds = new ComboPooledDataSource();
QueryRunner runner = new QueryRunner(ds);
// runner.update() 执行增删改
// runner.query() 执行查询语句
String sql = "insert into user(name,password) values('小周后','abcdefef')";
sql= "insert into user(name,password) values(?,?)";
sql = "select * from user";
// runner.update(sql); 执行增删改
// runner.update(sql,100,"ggggg");
// 执行查询语句,查询出来的数据,封装好返回
List<User> querys = runner.query(sql, new BeanListHandler<User>(
User.class));
System.out.println(querys);
ds.close();
}
 
}


 

 

(2)运行结果:

 

 


猜你喜欢

转载自blog.51cto.com/13501268/2128901