Maven 简介
Maven是一种程序开发的辅助工具,可以帮助我们管理需要的第三方包(类库)。
Maven工作原理:
1、在maven项目中,配置需要用到的包的名称。
2、maven 首先会在本地仓库中查找是否存在该包,如果存在则直接导入引用;如果不存在,则会从中央仓库先下载到本地仓库,再导入到项目中。
jar包:普通应用程序(通过main方法来运行的程序)
war包:web应用程序(通过servlet容器来运行的程序)
Maven引入步骤:
1 引入项目需要的jar包:右击项目->build path ->library 选项卡
2 更改JDK版本: library/选择jdk
JDBC 提炼
概念
-
JDBC是 JAVA官方定义的一组JAVA程序连接数据库的接口(为了对不同数据库提供统一的操作方法),接口的具体实现则交给各个数据库厂商。
-
DriverManager:用于管理JDBC的服务类,主要用于获取Connection连接对象。
-
Connection :代表数据库链接对象,每个Connection代表一个物理连接会话,想要访问数据库,必须获得连接。主要有以下功能:
- 创建Statement、PreparedStatement、CallableStatement对象
- 事务管理。setAutoCommit(false);
- Statement 是 Java 执行数据库操作的一个重要接口,用于在已经建立数据库连接的基础上,向数据库发送要执行的SQL语句。 Statement 对象,用于执行不带参数的简单SQL语句。
Statement对象的方法:
ResultSet executeQuery(String sql);//执行DQL语言
int executeUpdate(String sql); //执行DDL和DML,返回受影响的行数,执行DDL后返回0,执行DML后返回受影响的行数
boolean execue(String sql);//可以执行任何sql
- PreparedStatement:预编译的Statement对象。
- PreparedStatement接口是Statement的子接口,可以预编译SQL语句,被预编译的SQL语句存储在PreparedStatement对象中,然后可以使用该对象多次高效的执行SQL。
- PreparedStatement 也提供了execute() 和 executeUpdate();
String insertSql = "insert into tb_user(username,password,birthday) values (?,?,?)";
PreparedStatement pstm = conn.prepareStatement(insertSql);
pstm.setString(1, "zhsng");
pstm.setString(2, "12345");
pstm.setDate(3, new Date(0));
pstm.executeUpdate();
3 使用PreparedStatement有以下好处:
- 无需编译SQL语句,性能更好。
- 无需拼接SQL,编程更加简单。
- 可以防止SQL注入,安全性更好。
JDBC 操作步骤:
- 加载数据库厂商的类;Class.forName();
- 创建数据库连接 ( DriverManager -> Connection ):注意 (1) 编码格式 (2)添加一个时区
- 创建 Statement 对象( Connection -> Statement ),用来操作sql语句。 execute() 执行DML、DDL语言; execureQuery() 执行DQL语言。
- 执行查询时,会返回ResultSet,( Statement -> ResultSet )其中包含了查询的结果。
Junit: @Test 编写普通测试 @Before 在Test执行之前先执行 @After 在Test执行之后执行
与数据库建立连接 代码
/**
* 创建数据库链接
* @author lenovo
*
*/
package com.neuedu.jdbclearn;
import java.sql.Connection;
import java.sql.DriverManager;
public class Dababase {
public static Connection getConn(){
Connection conn = null;
try {
Class.forName("com.mysql.cj.jdbc.Driver").newInstance(); //反射,Class类创建驱动
conn = DriverManager.getConnection("jdbc:mysql://localhost:3306/shop?user=root&password="
+ "&serverTimezone=GMT&characterEncoding=utf8"); //驱动建立链接
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return conn;
}
public static void main(String[] args){
System.out.println(getConn());
}
}
运用连接进行操作 代码
1. Statement
package jdbclearn.test;
import java.sql.Connection;
//......
public class UserTest {
private Connection conn;
@Before
public void init(){
conn = Database.getConn();
}
@Test
public void testInsert(){
Course course = new Course();
course.setCno("4");
course.setCname("Python");
course.setTno("1");
try {
Statement stmt = conn.createStatement();
String insert = "insert into course(cno,cname,tno) values('"+course.getCno()+"','"+course.getCname()+"','"+course.getTno()+"');";
System.out.println(insert);
stmt.execute(insert);
} catch (Exception e) {
e.printStackTrace();
}finally{
if(conn!=null){
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
}
@Test
public void testSelect(){
try {
Statement stmt = conn.createStatement();
String select = "select * from course where tno = '4'";
ResultSet rs = stmt.executeQuery(select);
Course course = new Course();
while(rs.next()){
course.setCno(rs.getString("cno"));
course.setCname(rs.getString("cname"));
course.setTno(rs.getString("tno"));
System.out.println(course);
}
} catch (Exception e) {
e.printStackTrace();
}finally{
if(conn!=null){
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
}
}
2. PreparedStatement
PreparedStatement pstmt = conn.prepareStatement(sql);
pstmt.setString(1, param);
ResultSet rs = pstmt.executeQuery(sql);
List<Course> list = new ArrayList<Course>();
while(rs.next()){
Course course = new Course();
course.setCno(rs.getString("cno"));
course.setCname("cname");
course.setTno("tno");
list.add(course);
}
封装操作
1、先构建PreparedStatement 对象 -->查询结果
2、解析结果,将结果集中的每一行解析为一个对象
具体步骤
- 如何创建这个对象?
–> class对象 --> 反射 -->new Instance
; - 如何将数据放到创建出来的对象当中?
如何取出表里的数据–>需要什么?
列名 -->这列的类型
如何把数据放到java对象中–>
获取java类中的属性名–>获取属性类型–> 反射
–>调用set方法,将查找到的值放到java对象中–>反射 - 将对象放到list中,返回。
package com.neuedu.util;
import java.lang.reflect.Field;
//.......
public class DBHelper {
// select *from tb_ds where param1 = '1' and param2 = ?
public static <T> List<T> query(String sql,String[] params,Class<?> clz) {
Connection conn = Database.getConn();
List<T> result = new ArrayList<T>();
try {
//构建sql
PreparedStatement pstmt = conn.prepareStatement(sql);
for(int i = 0; i < params.length; i++) {
String param = params[i];
pstmt.setString(i + 1, param);
}
// 查询结果
ResultSet rs = pstmt.executeQuery();
while(rs.next()) {
//构建返回对象
ResultSetMetaData mdata= pstmt.getMetaData();
T instance = (T) clz.newInstance();
for(int i = 0; i < mdata.getColumnCount(); i++) {
String columName = mdata.getColumnName(i + 1).toLowerCase();
//获取属性类型
String fieldName = NameUtil.toCamel(columName, false);
Field field = clz.getDeclaredField(fieldName);
String type = field.getType().getTypeName();
Object value = null;
if(type.equals("int")) {
value = rs.getInt(columName);
}
if(type.equals("java.util.Date")) {
value = rs.getDate(columName);
}
if(type.equals("java.lang.String")) {
value = rs.getString(columName);
}
if(type.equals("java.lang.Double")) {
value = rs.getDouble(columName);
}
String setMethod = "set" + NameUtil.toCamel(columName, true);
Method method = clz.getDeclaredMethod(setMethod, field.getType());
method.invoke(instance, value);
}
result.add(instance);
}
} catch (Exception e) {
e.printStackTrace();
throw new RuntimeException("查询异常~~");
}
return result.size() == 0 ? null : result;
}
//测试
public static void main(String[] args) {
String sql1 = "select * from course where cno = ?";
String[] params1 = {"001"};
List<Course> courses = DBHelper.query(sql1, params1, Course.class);
System.out.println(courses);
}
}
JDBC操作事务:
四大性质:
Atomicity 原子性
一致性 Consistancy
隔离性 Isolation
持续性 Durability
Connection ->
开启 事务: setAutoCommit(false);
提交事务: commit();
回滚事务: rollback(); // 回到未执行代码之前,保证原子性
数据库连接池:
概念
背景:数据库连接的建立和关闭是一项十分耗费资源的操作,在网络服务环境中,数据库建立和关闭的操作往往容易称为系统的瓶颈。为了减少数据库的建立和关闭操作,JDBC2.0以后,引入了数据库连接池技术。
原理:系统启动的时候先建立多个连接并缓存,当用户使用时,从缓存中取出连接;使用后不是关闭,而是直接归还到缓存中,以供下次接着使用。
数据库连接池参数:
- 数据池的初始连接数
- 数据池的最大连接数
- 数据池的最小连接数
- 数据池每次增加的容量
数据库链接池的实现
JDBC使用javax.sql.DataSource
来表示数据库连接池,DataSource
是一个**接口**,该接口 通常由第三方来提供实现。
常见的第三方实现有DBCP和C3P0等,需下载相应 DBCP jar包
public class D {
private static BasicDataSource ds = new BasicDataSource();
static {
//加载数据库厂商驱动
ds.setDriverClassName("com.mysql.cj.jdbc.Driver");
//设置数据库地址
ds.setUrl("jdbc:mysql://localhost:3306/trt?serverTimezone=UTC");
ds.setUsername("root");
ds.setPassword("");
ds.setInitialSize(5); //初始化5个
ds.setMaxIdle(20); //最大20个
ds.setMinIdle(5); //最小5个
}
//取链接
public static Connection getConn() throws SQLException {
System.out.println(ds.getMaxTotal());
return ds.getConnection();
}
//归还链接到数据池
public static void returnConn(Connection conn) {
if(conn != null)
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
//测试
public static void main(String[] args) throws SQLException {
Connection conn = getConn();
returnConn(conn);
}
}