索引

MySQL官方对索引的定义为:索引(index)是帮助MySQL高效获取数据的的数据结构,提取句子主干,就可以得到作用的本质,索引是数据结构。

索引的分类

  • 主键索引:PRIMARY KEY

    • 唯一的标识,主键不可重复,只能由一个列作为索引
  • 唯一索引:UNIQUE KEY
    • 避免重复的列出现,唯一索引可以重复,多个列都可以标识为唯一索引
  • 常规索引:KEY/INDEX
    • 默认的,index,key关键字设置
  • 全文索引:FullText
    • 在特定的数据库引擎下才有
    • 快速定位数据

基础语法

--索引的使用
--在创建表的时候给字段增加索引 或创建完表后增加
USE school
SHOW INDEX FROM student1 --增加索引
ALTER TABLE `student1` ADD FULLTEXT INDEX `studentname`(`studentname`) --EXPLAIN 分析sql执行的状况
EXPLAIN SELECT * FROM `student1` --非全文索引 EXPLAIN SELECT * FROM student1 WHERE MATCH(studentname) AGAINST('韩')

测试索引

--测试索引
CREATE TABLE `app_user`(
`id` INT(4) UNSIGNED NOT NULL AUTO_INCREMENT,
`name` VARCHAR(20) DEFAULT'' COMMENT'用户姓名',
`email` VARCHAR(20) NOT NULL COMMENT'用户邮箱',
`phone` VARCHAR(20) DEFAULT'' COMMENT'用户电话',
`gender` TINYINT(4) UNSIGNED DEFAULT'0' COMMENT'性别(1是男,2是女)',
`password` VARCHAR(50) NOT NULL COMMENT '密码',
`age` INT(3) DEFAULT'0' COMMENT'年龄',
`create_time` DATETIME DEFAULT CURRENT_TIMESTAMP,
`update_name` TIMESTAMP NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
PRIMARY KEY(`id`)
)ENGINE INNODB DEFAULT CHARSET=utf8mb4 COMMENT'app用户表' --插入100万条数据
--写函数之前必须写 标志
DELIMITER $$
CREATE FUNCTION mock_dat() #创建一个函数
RETURNS INT
BEGIN
DECLARE num INT DEFAULT 1000000;
DECLARE i INT DEFAULT 0;
WHILE i<num DO
INSERT INTO `app_user`(name,email,phone,gender,password,age)
VALUES(CONCAT('用户',i),'813794474@qq.com',CONCAT('18',FLOOR(RAND()*((999999999-1000000000)+1000000000))),
FLOOR((RAND()*2)+1),UUID(),FLOOR(RAND()*100));
SET i=i+1;
END WHILE;
RETURN i;
END;
--
SELECT mock_dat(); SELECT * FROM app_user WHERE name = '用户9999';
EXPLAIN SELECT * FROM app_user WHERE name = '用户9999';
EXPLAIN SELECT * FROM app_user WHERE name = '用户1'; --创建索引 id_表名_字段名 on 表(字段)
CREATE INDEX id_app_user_name ON app_user(`name`); SELECT * FROM app_user WHERE name = '用户9999';
EXPLAIN SELECT * FROM app_user WHERE name = '用户9999';

索引在小数据的时候用处不大,在大数据的时候,区别十分明显。

索引原则

  • 索引不是越多越好
  • 不要对经常变动的数据加索引
  • 小数据量的表不需要加索引
  • 索引一般加在常用来查询的字段上

索引的数据结构

Hash 类型的索引

Btree:innodb默认的数据结构

权限管理和备份

点击用户进去可以选择新增用户,在服务器权限中可以给用户设置不同的权限。

也可以使用SQL赋予每个用户权限

--创建用户
CREATE USER zhou IDENTIFIED BY '123456' --修改当前用户密码
SET PASSWORD = PASSWORD('111111') --修改指定用户密码
SET PASSWORD FOR zhou = password('111111') --重命名
RENAME USER zhou TO zzzz --用户授权 授予全部的权限
--ALL PRIVILEGES除了给别人授权都可以
GRANT ALL PRIVILEGES ON *.* TO zzzz --查看指定用户权限
SHOW GRANTS FOR zzzz
--查看管理员权限
SHOW GRANTS FOR root@localhost --root用户权限 GRANT ALL PRIVILEGES ON *.* TO 'root'@'localhost' WITH GRANT OPTION --撤销权限
REVOKE ALL PRIVILEGES *.* FROM zzzz --删除用户
DROP zzzz

备份

为什么备份:

  • 保证重要的数据不丢失
  • 数据转移

MySQL数据库备份的方式

  • 直接拷贝物理文件

  • 在可视化工具中手动导出数据库

    • 在想要导出的表或者库中,右键选择转储sql文件
  • 使用命令行导出 mysqldump 命令行使用

    --mysqldump -h主机 -u用户名 -p密码 数据库 表名 >物理磁盘位置/文件名
    mysqldump -hlocalhost -uroot -p123456 school student1 > D:/a.sql --mysqldump -h主机 -u用户名 -p密码 数据库 表名1 表名2 >物理磁盘位置/文件名
    mysqldump -hlocalhost -uroot -p123456 school student1 subject > D:/b.sql --mysqldump -h主机 -u用户名 -p密码 数据库 >物理磁盘位置/文件名
    mysqldump -hlocalhost -uroot -p123456 school > D:/c.sql --导入表
    --登录
    mysql -uroot -p123456
    use school;
    sourse d/a.sql 或
    mysql -u用户名 -p密码 库名 表名<文件路径

规范数据库设计

当数据库比较复杂的时候,需要按规范设计。

糟糕的数据库设计:

  • 数据冗余,浪费空间
  • 数据插入和删除都麻烦【阿里巴巴开发手册 屏蔽使用外键】
  • 系统的性能差

良好的数据库设计:

  • 节省内存空间
  • 保证数据库的完整性
  • 性能好,便于开发

软件开发中关于数据库的设计

  • 分析需求:分析业务和需要处理的数据库的需求
  • 概要设计:设计关系图E-R图

设计数据库的步骤:(个人博客)

  • 收集信息,分析需求

    • 用户表(用户登录注册,个人信息,写博客,创建分类)
    • 分类表(文章分类,博客作者)
    • 文章表(文章信息)
    • 友链表(友链信息)
    • 评论表 (评论信息)
    • 自定义表(可选) (存储其他信息)
  • 标识实体(把需求写到字段)
  • 标识实体之间的关系
    • 写博客:user-->blog
    • 创建分类:user-->category
    • 友链:link
    • ...

三大范式

第一范式(1NF):原子性,要求数据库表的每一列都是不可分割的原子数据项。

第二范式(2NF):满足第一范式,非码属性必须完全依赖于候选码,确保数据库表中的每一列都和主键相关,而不能只与主键的某一部分相关。即每张表只描述一件事情。

第三范式(3NF):满足第一第二范式,任何非主属性不依赖于其它非主属性(即消除传递依赖),第三范式需要确保数据表中每一列数据都与主键直接相关,而不能间接相关。

规范性和性能问题:(关联查询的表不得超过三张表 阿里规约)

  • 考虑商业化需求和目标(成本,用户体验),数据库的性能更加重要
  • 在规范性能需求的时候,需要适当考虑一下规范性
  • 在有些情况下,故意给表增加一些冗余字段(多表查询变为单表查询),提高效率
  • 故意增加一些计算列(从大数据量降为小数据量的一些查询)

JDBC

数据库驱动:应用程序和数据库之间需要有驱动来进行连接。

SUN公司为了简化开发人员的(对数据库的统一)操作,提供了一个(Java操作数据库)规范,俗称JDBC。

这些规范的具体实现由数据库厂商去做。

对于开发人员来说只需掌握JDBC接口的操作即可。

java.sql javac.sql

JDBC程序

创建lib目录,在lib下放入mysql-connector-java-5.1.47.jar,右击lib,add as library。

  • 加载驱动
  • 连接数据库 DriverManager
  • 获得执行sql的对象 statement
  • 获得返回的结果值
  • 释放连接
package com.zr.lesson01;

import java.sql.*;

public class JdbcDemo01 {
public static void main(String[] args) throws ClassNotFoundException, SQLException {
//加载驱动
Class.forName("com.mysql.jdbc.Driver"); //用户信息和Url
String url = "jdbc:mysql://localhost:3306/jdbcStudy?useUnicode=true&characterEncoding=utf8&useSSL=false";
String username = "root";
String password = "123456"; //连接成功 数据库对象 DriverManager驱动管理
Connection connection = DriverManager.getConnection(url, username, password);
//执行sql的对象
Statement statement = connection.createStatement();
//执行sql
String sql = "select * from users";
ResultSet resultSet = statement.executeQuery(sql); //返回的结果集
while (resultSet.next()){
System.out.println("id="+resultSet.getObject("id"));
System.out.println("name="+resultSet.getObject("name"));
System.out.println("pwd="+resultSet.getObject("password"));
System.out.println("email="+resultSet.getObject("email"));
System.out.println("birthday="+resultSet.getObject("birthday"));
System.out.println("======================================");
}
//释放连接 耗资源 用完就关掉
resultSet.close();
statement.close();
connection.close();
}
} //MySQL默认端口号3306 //Oracle ---1521
//jdbc:oracle:thin:@localhost:1521:sid
connection.commit(); //事务提交
connection.rollback(); //事务回滚
connection.setAutoCommit(true); //开启事务提交 statement.executeQuery(); //查询操作返回 resultset
statement.executeUpdate(); //更新,插入,删除都用这个,返回一个受影响的行数
statement.execute(); //执行任何sql resultset 查询的结果集,封装了所有的查询结果集
resultSet.getObject();//在不知道列类型的情况下使用
//知道列的指定类型
resultSet.getString();
resultSet.getInt();
resultSet.getDate(); resultSet.beforeFirst();//移动到最前面
resultSet.afterLast();//移动到最后面
resultSet.next();//移动到下一个
resultSet.previous();//移动到前一个
resultSet.absolute(row);//移动到指定行

Statement对象

jdbc中的statement对象用于向数据库发送sql语句,想完成对数据库的增删改查只需发送相应的sql语句即可。

executeUpdate执行完后,返回一个整数(即sql语句导致几行数据发生了变化)。

executeQuery执行完后,返回代表查询结果的resultset对象。

CRUD操作:create,使用Statement(sql)方法完成对数据库的添加操作,示例如下:

Statement st = connection.createStatement;
String sql = "insert into user(...) values(...) "
int num = st.executeUpdate(sql);
if(num>0){
System.out.println("插入成功!")
}

CRUD操作:delete,使用Statement(sql)方法完成对数据库的删除操作,示例如下:

Statement st = connection.createStatement;
String sql = "delete from user wherte id=1"
int num = st.executeUpdate(sql);
if(num>0){
System.out.println("删除成功!")
}

CRUD操作:update,使用Statement(sql)方法完成对数据库的修改操作,示例如下:

statement st = connection.Statement;
String sql = "update user set name=`` where id=1"
int num = st.executeUpdate;
if(num>0){
System.out.println("修改成功!");
}

CRUD操作:read,使用Statement(sql)方法完成对数据库的查询操作,示例如下:

Statement st = connection.createStatement;
String sql = "select * from user "
Resultset rs = st.executeQuery(sql);
if(rs.next()){
//根据获取的数据类型,分别调用rs的相应方法映射到Java对象中
}

工具类实现

先创建一个jdbcStudy数据库,再创建一个users用户表,表中的字段为id,name,password,emain,birthday

配置MySQL数据库文件,创建工具类

配置文件

driver=com.mysql.jdbc.Driver
url=jdbc:mysql://localhost:3306/jdbcStudy?useunicode=true&characterEncoding=utf8&useSSL=false
username=root
password=123456

工具类

package com.zr.lesson02.utils;
//工具类
import java.io.IOException;
import java.io.InputStream;
import java.sql.*;
import java.util.Properties; public class JdbcUtils { private static String driver = null;
private static String url = null;
private static String username = null;
private static String password = null; static {
try {
//读取资源
InputStream in = JdbcUtils.class.getClassLoader().getResourceAsStream("db.properties");
Properties properties = new Properties();
properties.load(in); driver = properties.getProperty("driver");
url = properties.getProperty("url");
username = properties.getProperty("username");
password = properties.getProperty("password"); //驱动只用加载一次
Class.forName(driver);
} catch (Exception e) {
e.printStackTrace();
}
}
//获取连接
public static Connection getConnection() throws SQLException {
return DriverManager.getConnection(url,username,password);
} //释放连接
public static void release(Connection con, Statement st, ResultSet rs) throws SQLException {
if (rs!=null){
rs.close();
}
if (st!=null){
st.close();
}
if (con!=null){
con.commit();
}
}
}

增加数据

package com.zr.lesson02.utils;

import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
//插入数据
public class TestInsert {
public static void main(String[] args) throws Exception {
Connection con = null;
Statement st = null;
ResultSet rs = null;
try {
con = JdbcUtils.getConnection(); //获取数据库连接
st = con.createStatement();//创建执行sql的对象
String sql = "insert into users values(5,'赵云','111111','111@qq.com','2020-01-01')";
int i = st.executeUpdate(sql);//执行sql
if (i>0){
System.out.println("插入成功!");
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}finally {
JdbcUtils.release(con,st,rs); }
}
}

删除数据

package com.zr.lesson02.utils;

import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
//删除数据
public class TestDelete {
public static void main(String[] args) throws SQLException {
Connection con = null;
Statement st = null;
ResultSet rs = null;
try {
con = JdbcUtils.getConnection();//获取数据库连接
st = con.createStatement();//创建执行sql的对象
String sql = "delete from users where id=5";
int i = st.executeUpdate(sql);
if (i>0){
System.out.println("删除创建!");
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}finally {
JdbcUtils.release(con,st,rs);
}
}
}

修改数据

package com.zr.lesson02.utils;

import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
//修改数据
public class TestUpdate {
public static void main(String[] args) throws SQLException {
Connection con = null;
Statement st = null;
ResultSet rs = null; try {
con = JdbcUtils.getConnection();//获取数据库连接
st = con.createStatement();//创建执行sql的对象
String sql = "update users set name='韩信' where id=4";
int i = st.executeUpdate(sql);
if (i>0){
System.out.println("更新成功!");
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}finally {
JdbcUtils.release(con,st,rs);
}
}
}

添加数据

package com.zr.lesson02.utils;

import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
//查询数据
public class TestSelect {
public static void main(String[] args) throws SQLException {
Connection con = null;
Statement st = null;
ResultSet rs = null; try {
con = JdbcUtils.getConnection();//获取数据库连接
st = con.createStatement();//创建执行sql的对象
String sql = "select * from users";
rs = st.executeQuery(sql);
//if只能查出一条数据 这里查询所有用户信息使用while
while (rs.next()){
System.out.println("id="+rs.getInt("id"));
System.out.println("name="+rs.getString("name"));
System.out.println("password="+rs.getString("password"));
System.out.println("email="+rs.getString("email"));
System.out.println("birthday="+rs.getDate("birthday"));
System.out.println("==========================");
}
System.out.println("查询成功!");
} catch (SQLException throwables) {
throwables.printStackTrace();
}finally {
JdbcUtils.release(con,st,rs);
}
}
}

sql注入

sql存在漏洞,会被攻击导致数据泄露,sql会被拼接。

package com.zr.lesson02.utils;

import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
//sql注入
public class SqlInjection {
public static void main(String[] args) throws SQLException {
//正常登录 数据库中有的用户和密码
//login("韩信","111111"); //sql注入 会输出所有密码为123456的人的信息
login("'or'1=1","123456"); //sql注入 会查询所有信息
//login("'or'1=1","'or='1=1");
}
//登录业务
public static void login(String username,String password) throws SQLException {
Connection con = null;
Statement st = null;
ResultSet rs = null; try {
con = JdbcUtils.getConnection();//获取数据库连接
st = con.createStatement();//创建执行sql的对象
//select * from users where name=''or'1=1' and password='123456'
//select * from users where name=''or'1=1' and password=''or'1=1'
String sql = "select * from users where name='"+username+"' and password='"+password+"'";
rs = st.executeQuery(sql);
//if只能查出一条数据 这里查询所有用户信息使用while
while (rs.next()){
System.out.println("id="+rs.getInt("id"));
System.out.println("name="+rs.getString("name"));
System.out.println("password="+rs.getString("password"));
System.out.println("email="+rs.getString("email"));
System.out.println("birthday="+rs.getDate("birthday"));
System.out.println("==========================");
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}finally {
JdbcUtils.release(con,st,rs);
}
}
}

PreparedStatement对象

PreparedStatement可以防止sql注入,而且效率更高。实例如下:

增加数据:

package com.zr.lesson03;

import com.zr.lesson02.JdbcUtils;
import java.util.Date;
import java.sql.*; //PreparedStatement 插入
public class TestInsert {
public static void main(String[] args) throws SQLException {
Connection con = null;
PreparedStatement ps = null;
ResultSet rs = null;
try {
con = JdbcUtils.getConnection();
//区别
String sql = "insert into users values(?,?,?,?,?)";//使用?占位符 代替参数
ps = con.prepareStatement(sql);//预编译 先写sql 然后不执行 //手动给参数赋值
ps.setInt(1,5);
ps.setString(2,"李白");
ps.setString(3,"123333");
ps.setString(4,"813794474@qq.com");
//sql.Date 数据库 java.sql.date()
//util.Date Java new date().gettime() 获得时间戳
ps.setDate(5,new java.sql.Date(new Date().getTime())); //执行
int i = ps.executeUpdate();
if (i>0){
System.out.println("插入成功!");
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}finally {
JdbcUtils.release(con,ps,rs);
}
}
}

删除数据:

package com.zr.lesson03;

import com.zr.lesson02.JdbcUtils;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Date; //PreparedStatement 删除
public class TestDelete {
public static void main(String[] args) throws SQLException {
Connection con = null;
PreparedStatement ps = null;
ResultSet rs = null;
try {
con = JdbcUtils.getConnection();
//区别
String sql = "delete from users where id=?";//使用?占位符 代替参数
ps = con.prepareStatement(sql);//预编译 先写sql 然后不执行 //手动给参数赋值
ps.setInt(1,5); //执行
int i = ps.executeUpdate();
if (i>0){
System.out.println("删除成功!");
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}finally {
JdbcUtils.release(con,ps,rs);
}
}
}

修改数据:

package com.zr.lesson03;

import com.zr.lesson02.JdbcUtils;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException; //PreparedStatement 修改
public class TestUpdate {
public static void main(String[] args) throws SQLException {
Connection con = null;
PreparedStatement ps = null;
ResultSet rs = null;
try {
con = JdbcUtils.getConnection();
//区别
String sql = "update users set name = ? where id = ?;";//使用?占位符 代替参数
ps = con.prepareStatement(sql);//预编译 先写sql 然后不执行 //手动给参数赋值
ps.setString(1,"关羽");
ps.setInt(2,3); //执行
int i = ps.executeUpdate();
if (i>0){
System.out.println("修改成功!");
}
} catch (SQLException throwables) {
throwables.printStackTrace();
}finally {
JdbcUtils.release(con,ps,rs);
}
}
}

查询数据:

package com.zr.lesson03;

import com.zr.lesson02.JdbcUtils;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException; //查询
public class TestSelect {
public static void main(String[] args) throws SQLException {
Connection con = null;
PreparedStatement ps = null;
ResultSet rs = null;
try {
con = JdbcUtils.getConnection();
String sql = "select * from users where id=?";
ps = con.prepareStatement(sql);
ps.setInt(1,3);
rs = ps.executeQuery();
if (rs.next()){
System.out.println("name="+rs.getString("name"));
System.out.println("password="+rs.getString("password"));
} } catch (SQLException throwables) {
throwables.printStackTrace();
}finally {
JdbcUtils.release(con,ps,rs);
}
}
}

事务

要么都成功,要么都失败。

ACID原则:原子性(要么都成功,要么都失败),一致性(保持最终结果的一致性),持久性(一旦提交不可逆,持久到数据库),隔离性(多个进程互不干扰)。

隔离性的问题:

  • 脏读:一个事务读取了另一个没有提交的事务
  • 虚读(幻读):在一个事务内读取到了别人插入的数据,导致前后读出来的数据不一致
  • 不可重复读:在同一个事务内,重复读取了表中的数据,表数据发生了改变
package com.zr.lesson04;

import com.zr.lesson02.JdbcUtils;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
//模拟转账成功
public class TestTransaction {
public static void main(String[] args) throws SQLException {
Connection con = null;
PreparedStatement st = null;
ResultSet rs = null;
try {
con = JdbcUtils.getConnection();
//关闭数据库的自动提交功能,自动开启事务
con.setAutoCommit(false);
//执行业务
String sql1 ="update account set money = money-100 where name = 'libai'";
st = con.prepareStatement(sql1);
st.executeUpdate(); String sql2 ="update account set money = money+100 where name = 'hanxin'";
st = con.prepareStatement(sql2);
st.executeUpdate(); //业务完毕 提交事务
con.commit();
System.out.println("成功!");
} catch (SQLException throwables) {
try {
con.rollback(); //失败就回滚事务
} catch (SQLException e) {
e.printStackTrace();
}
throwables.printStackTrace();
}finally {
JdbcUtils.release(con,st,rs);
}
}
}

模拟转账失败

package com.zr.lesson04;

import com.zr.lesson02.JdbcUtils;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException; //模拟转账失败
public class TestTransaction02 {
public static void main(String[] args) throws SQLException {
Connection con = null;
PreparedStatement st = null;
ResultSet rs = null;
try {
con = JdbcUtils.getConnection();
//关闭数据库的自动提交功能,自动开启事务
con.setAutoCommit(false);
//执行业务
String sql1 ="update account set money = money-100 where name = 'libai'";
st = con.prepareStatement(sql1);
st.executeUpdate(); int x=1/0;//报错 String sql2 ="update account set money = money+100 where name = 'hanxin'";
st = con.prepareStatement(sql2);
st.executeUpdate(); //业务执行完毕 提交事务
con.commit();
System.out.println("成功!");
} catch (Exception e) {
//默认会自动回滚 也可以显式定义
/* try {
con.rollback(); //失败就回滚事务
} catch (SQLException e2) {
e2.printStackTrace();
}*/
e.printStackTrace();
}finally {
JdbcUtils.release(con,st,rs);
}
}
}

数据库连接池

数据库连接---执行完毕---释放 连接释放是十分浪费系统资源的。

池化技术:准备一些预先的资源,过来连接已经准备好的。

编写连接池,实现一个接口DataSource。

开源数据源实现:

  • DBCP
  • C3P0
  • Durid(阿里巴巴)

DBCP

使用这些数据库连接池之后,我们在项目开发中就不需要编写数据库连接的代码了。

DBCP:lib下导入 commens-dbcp-1.4.jar和commens-pool-1.6.jar

创建dbconfig.properties文件

#连接设置
driverClassname=com.mysql.jdbc.Driver
url=jdbc:mysql://localhost:3306/jdbcStudy?useunicode=true&characterEncoding=utf8&useSSL=false
username=root
password=123456 #初始化连接
initialSize=10 #最大连接数量
maxActive=50 #最大空闲连接
maxIdle=20 #超时等待时间 毫秒
maxWait=60000 connectionProperties=useUnicode=true;characterEncoding=utf8 defaultAutoCommit=true defaultReadOnly= defaultTransactionIsolation=READ_UNCOMMITTED

创建DBCP工具类

package com.zr.lesson05;

import org.apache.commons.dbcp.BasicDataSource;
import org.apache.commons.dbcp.BasicDataSourceFactory; import javax.sql.DataSource;
import java.io.InputStream;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Properties; public class JdbcUtils_DBCP {
private static DataSource dataSource = null;
static{
try{
InputStream in = JdbcUtils_DBCP.class.getClassLoader().getResourceAsStream("dbconfig.properties");
Properties properties = new Properties();
properties.load(in); //创建数据源 工厂模式
dataSource = BasicDataSourceFactory.createDataSource(properties);
}catch (Exception e){
e.printStackTrace();
}
} public static Connection getConnection() throws SQLException {
return dataSource.getConnection(); //从数据源中获取连接
}
public static void release(Connection con, Statement st, ResultSet rs){
if (con!=null){
try {
con.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
if (st!=null){
try {
con.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
if (rs!=null){
try {
con.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
}
}

测试插入数据

package com.zr.lesson05;

import com.zr.lesson02.JdbcUtils;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Date; public class TestDBCP {
public static void main(String[] args) throws SQLException {
Connection con = null;
PreparedStatement ps = null;
ResultSet rs = null;
try {
con = JdbcUtils_DBCP.getConnection();
//区别
String sql = "insert into users values(?,?,?,?,?)";//使用?占位符 代替参数
ps = con.prepareStatement(sql);//预编译 先写sql 然后不执行 //手动给参数赋值
ps.setInt(1, 5);
ps.setString(2, "李白");
ps.setString(3, "123333");
ps.setString(4, "813794474@qq.com");
//sql.Date 数据库 java.sql.date()
//util.Date Java new date().gettime() 获得时间戳
ps.setDate(5, new java.sql.Date(new Date().getTime())); //执行
int i = ps.executeUpdate();
if (i > 0) {
System.out.println("插入成功!");
}
} catch (SQLException throwables) {
throwables.printStackTrace();
} finally {
JdbcUtils_DBCP.release(con, ps, rs);
}
}
}

C3P0

C3P0:lib下导入c3p0-0.9.5.5.jar和mchange-commens-java-0.2.19.jar

先创建c3p0-config.xml文件,再创建JdbcUtils_C3P0工具类

<?xml version="1.0" encoding="UTF-8"?>
<c3p0-config>
<!-- 默认配置,如果没有指定则使用这个配置 -->
<default-config>
<property name="driverClass">com.mysql.jdbc.Driver</property>
<property name="jdbcUrl">jdbc:mysql://localhost:3306/jdbcStudy</property>
<property name="user">root</property>
<property name="password">123456</property> <property name="acquirIncrement">5</property>>
<property name="initialPoolSize">10</property>
<property name="maxPoolSize">20</property>
<property name="minPoolSize">5</property>
</default-config>
<!-- 命名的配置,可以通过方法调用实现 -->
<named-config name="Mysql">
<property name="driverClass">com.mysql.jdbc.Driver</property>
<property name="jdbcUrl">jdbc:mysql://localhost:3306/jdbcStudy</property>
<property name="user">root</property>
<property name="password">123456</property> <!-- 如果池中数据连接不够时一次增长多少个 -->
<property name="acquireIncrement">5</property>
<!-- 初始化数据库连接池时连接的数量 -->
<property name="initialPoolSize">10</property>
<!-- 数据库连接池中的最大的数据库连接数 -->
<property name="maxPoolSize">25</property>
<!-- 数据库连接池中的最小的数据库连接数 -->
<property name="minPoolSize">5</property>
</named-config>
</c3p0-config>

创建C3P0工具类

package com.zr.lesson05;

import com.mchange.v2.c3p0.ComboPooledDataSource;
import org.apache.commons.dbcp.BasicDataSourceFactory; import javax.sql.DataSource;
import java.io.InputStream;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Properties; public class JdbcUtils_C3P0 {
private static ComboPooledDataSource dataSource = null;
static{
try{
/*//代码配置
dataSource = new ComboPooledDataSource();
dataSource.setDriverClass();
dataSource.setUser();
dataSource.setPassword();
dataSource.setJdbcUrl(); dataSource.setMaxPoolSize();
dataSource.setMinPoolSize();*/ dataSource = new ComboPooledDataSource("Mysql");//配置文件写法 //创建数据源 工厂模式 }catch (Exception e){
e.printStackTrace();
}
} public static Connection getConnection() throws SQLException {
return dataSource.getConnection(); //从数据源中获取连接
}
public static void release(Connection con, Statement st, ResultSet rs){
if (con!=null){
try {
con.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
if (st!=null){
try {
con.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
if (rs!=null){
try {
con.close();
} catch (SQLException throwables) {
throwables.printStackTrace();
}
}
}
}

测试插入代码

package com.zr.lesson05;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.Date; public class TestC3P0 {
public static void main(String[] args) throws SQLException {
Connection con = null;
PreparedStatement ps = null;
ResultSet rs = null;
try {
con = JdbcUtils_C3P0.getConnection();
//区别
String sql = "insert into users values(?,?,?,?,?)";//使用?占位符 代替参数
ps = con.prepareStatement(sql);//预编译 先写sql 然后不执行 //手动给参数赋值
ps.setInt(1, 6);
ps.setString(2, "李白");
ps.setString(3, "123333");
ps.setString(4, "813794474@qq.com");
//sql.Date 数据库 java.sql.date()
//util.Date Java new date().gettime() 获得时间戳
ps.setDate(5, new java.sql.Date(new Date().getTime())); //执行
int i = ps.executeUpdate();
if (i > 0) {
System.out.println("插入成功!");
}
} catch (SQLException throwables) {
throwables.printStackTrace();
} finally {
JdbcUtils_C3P0.release(con, ps, rs);
}
}
}

结论:无论使用什么数据源,本质还是一样的,DataSource不变,方法就不会变。

MySql学习笔记--详细整理--下的更多相关文章

  1. MySql学习笔记--详细整理--上

    目录 MySql MySql安装 连接数据库 操作数据库 数据库的列类型 数据库的字段属性 创建数据库 修改删除表 数据管理 外键 DML语言 添加 修改 删除 DQL查询数据(重点) 查询 去重 w ...

  2. mysql学习笔记(window下简单使用+Navict)

    之前安装过mysql.最近刚好要重新翻出来看看 发现又忘记了那些命令.还是要百度.所以不如自己整理下 尽管网上有很多相关的介绍.当时想对的不如自己整理出来的舒服 首先是下载安装.网上有很多就不一一罗列 ...

  3. mysql学习笔记(Centos下rpm编译配置+远程访问)

    新工作以来,博主感觉天天都很忙,博客已经好久没有写了 从昨天开始弄centos服务器中搭建mysql5.6,由于yum最新版本只有5.1的所以折腾到现在 首先看看是否已安装过其他版本的mysql [r ...

  4. mysql basic operation,mysql总结,对mysql经常使用语句的详细总结,MySQL学习笔记

    mysql> select * from wifi_data where dev_id like "0023-AABBCCCCBBAA" ; 1.显示数据库列表.show d ...

  5. 【mysql学习笔记整理】

    /*mysql学习笔记整理*/ /*常用的数据库操作对象*/ #库的操作#创建#数据库的创建USE mysql;CREATE DATABASE db_x;#删除#删除数据库DROP DATABASE ...

  6. 一千行MySQL学习笔记 (转)

    出处:  一千行MySQL学习笔记 /* 启动MySQL */ net start mysql /* 连接与断开服务器 */ mysql -h 地址 -P 端口 -u 用户名 -p 密码 /* 跳过权 ...

  7. Mysql学习笔记(三)对表数据的增删改查。

    正文内容. 这一部分是最简单的,也是最麻烦的.简单是因为其实只包括增删该插四个部分.大体上看,增加数据.删除数据.修改数据.查询数据都不麻烦啊,我们日常都是常用的.这个谁不会呢?以前在培训机构学mys ...

  8. MySQL学习笔记-数据库文件

    数据库文件 MySQL主要文件类型有如下几种 参数文件:my.cnf--MySQL实例启动的时候在哪里可以找到数据库文件,并且指定某些初始化参数,这些参数定义了某种内存结构的大小等设置,还介绍了参数类 ...

  9. 数据库MySQL学习笔记高级篇

    数据库MySQL学习笔记高级篇 写在前面 学习链接:数据库 MySQL 视频教程全集 1. mysql的架构介绍 mysql简介 概述 高级Mysql 完整的mysql优化需要很深的功底,大公司甚至有 ...

随机推荐

  1. java数据结构-08队列

    一.什么是队列 队列是一种特殊的线性表,只能在头尾两端进行操作,特点是先进先出:就像排队买票一样,先来的先买 二.接口设计  三.代码实现 可以使用动态数组.链表等实现:这里两种实现栈与双向链表 1. ...

  2. ansible-hoc命令行

    ansible一种开源的自动化工具 ansible: hoc命令行: 是一款开源的自动化运维工具 python paramiko #模拟ssh协议批量管理主机 jinja2 #模板语言,主要用来传递变 ...

  3. C语言知识点复习梳理

    C语言知识点复习梳理 C语言的知识点讲完了,接下来就是做一下整理与总结,然后就会进入其他知识的学习. 本文目录如下: 基础知识. 顺序程序设计. 数据类型. 标准输入输出. 进制转换. 选择结构. 循 ...

  4. Educational Codeforces Round 95 (Rated for Div. 2)

    CF的Educational Round (Div.2),质量还是蛮高的. A: 水题 #include<cstdio> #include<algorithm> typedef ...

  5. SharedPreferences源码分析

    分析达成目标 了解基本实现 SharePreferences是否线程安全 SharePreferences的mode参数是什么 了解apply与commit的区别 导致ANR的原因 Android8. ...

  6. SDOI征途--斜率优化

    题目描述 给定长为 n 的数列 a, 要求划分成 m 段,使得方差最小, 输出方差\(*m^2\) 题解 斜率优化好题 准备部分 设第 i 段长为 \(len_i\) 先考虑方差(\(S^2\))的式 ...

  7. redis方法-

    //链接错误注意 //1.防火墙 //2.配置文件IP绑定 $redis = new Redis(); //连接redis $redis->connect('127.0.0.1', 6379); ...

  8. Java获取不到Canal服务器端数据问题汇总(坑人的东西)

    情况1:(基本都是这样的问题,) 1.需要修改canal.properties配置 vim conf/canal.properties canal.instance.parser.parallelTh ...

  9. MIPS汇编及模拟器下载

    1. 简述汇编语言发展 在计算机发展初期,人们用0-1序列来表示每一条语言,亦即二进制的机器指令 由于机器指令过于繁琐,程序员们开发出了一种新的语言,这种用符号表示的计算机语言被称为汇编语言 计算机继 ...

  10. Tomcat 总结

    JavaWeb简介 JavaWeb,是用Java技术来解决相关web互联网领域的技术总和. Web包括:web服务器和web客户端两个部分,有两种软件架构 ​ C/S:客户端/服务器端 ​ B/S:浏 ...