0


JDBC---Java连接数据库

  • 第一章 JDBC概述

1.1 JDBC概述

jdbc是(Java Database Connectivity)单词的缩写,翻译为java连接数据库。是Java程序连接数据库的技术总称。
JDBC由两个部分组成:
①java语言的规范(接口)
②各个数据库厂商的实现驱动(jar)组成
所以不一定只连接MySQL,Java API中提供的是接口规范,导入不同数据库厂商的jar包,从不同的实现类里获取连接,就连接上了不同的数据库。
1.2 JDBC使用步骤

0.添加jar
1.注册驱动
2.获取连接Connection
3.编写SQL语句
4.创建预处理命令对象PreparedStatement
5.填参数
6.执行SQL语句,并返回结果(“增删改”返回影响行数,“查”返回结果集,解析结果集)
7.释放连接

JDBC在整体架构的位置:
在这里插入图片描述

  • 第二章 使用PreparedStatement处理CRUD

2.0简单的CRUD:
先提供一个实体类pojo:里面生成必要的方法

publicclassFruit{privateInteger fid;privateString fname;privateInteger price;privateInteger fcount;privateString remark;publicFruit(){}publicFruit(Integer fid,String fname,String remark){this.fid = fid;this.fname = fname;this.remark = remark;}publicFruit(Integer fid,String fname,Integer price,Integer fcount,String remark){this.fid = fid;this.fname = fname;this.price = price;this.fcount = fcount;this.remark = remark;}publicIntegergetFid(){return fid;}publicvoidsetFid(Integer fid){this.fid = fid;}publicStringgetFname(){return fname;}publicvoidsetFname(String fname){this.fname = fname;}publicIntegergetPrice(){return price;}publicvoidsetPrice(Integer price){this.price = price;}publicIntegergetFcount(){return fcount;}publicvoidsetFcount(Integer fcount){this.fcount = fcount;}publicStringgetRemark(){return remark;}publicvoidsetRemark(String remark){this.remark = remark;}@OverridepublicStringtoString(){return"Fruit{"+"fid="+ fid +", fname='"+ fname +'\''+", price="+ price +", fcount="+ fcount +", remark='"+ remark +'\''+'}';}}

添加数据:

publicstaticvoidmain(String[] args)throwsClassNotFoundException,SQLException{//1.加载驱动Class.forName("com.mysql.cj.jdbc.Driver");//2.通过驱动管理器获取连接对象Connection connection =DriverManager.getConnection("jdbc:mysql://localhost:3306/fruitdb?user=root&password=0630");//3.编写SQL语句String sql="insert into t_fruit values(0,?,?,?,?)";//4.创建预处理命令对象PreparedStatement preparedStatement = connection.prepareStatement(sql);//5.填充参数
        preparedStatement.setString(1,"榴莲");
        preparedStatement.setString(2,"15");
        preparedStatement.setString(3,"100");
        preparedStatement.setString(4,"榴莲是一种神奇的水果");//6.执行更新(增删改),返回影响行数int i = preparedStatement.executeUpdate();System.out.println(i>0?"添加成功":"添加失败");//7.释放资源
        preparedStatement.close();
        connection.close();}

更新数据:

publicstaticvoidmain(String[] args)throwsClassNotFoundException,SQLException{Fruit fruit=newFruit(33,"猕猴桃","猕猴桃营养价值很高");Class.forName("com.mysql.cj.jdbc.Driver");Connection connection =DriverManager.getConnection("jdbc:mysql://localhost:3306/fruitdb?user=root&password=0630");String sql="update t_fruit set fname=?,remark=? where fid=?";PreparedStatement preparedStatement = connection.prepareStatement(sql);
        preparedStatement.setString(1,fruit.getFname());
        preparedStatement.setString(2,fruit.getRemark());
        preparedStatement.setInt(3,fruit.getFid());int i = preparedStatement.executeUpdate();System.out.println(i>0?"修改成功":"修改失败");
        preparedStatement.close();
        connection.close();}

删除数据:

publicstaticvoidmain(String[] args)throwsClassNotFoundException,SQLException{Fruit fruit=newFruit(33,"猕猴桃","猕猴桃营养价值很高");Class.forName("com.mysql.cj.jdbc.Driver");Connection connection =DriverManager.getConnection("jdbc:mysql://localhost:3306/fruitdb?user=root&password=0630");String sql="delete from t_fruit where fid=?";PreparedStatement preparedStatement = connection.prepareStatement(sql);
        preparedStatement.setInt(1,fruit.getFid());int i = preparedStatement.executeUpdate();System.out.println(i>0?"删除成功":"删除失败");
        preparedStatement.close();
        connection.close();}

查询数据:把每一行的每一列都取出来,一次放一行数据到List中,最后将list打印。

publicstaticvoidmain(String[] args)throwsClassNotFoundException,SQLException{Class.forName("com.mysql.cj.jdbc.Driver");Connection connection =DriverManager.getConnection("jdbc:mysql://localhost:3306/fruitdb?user=root&password=0630");String sql="select * from t_fruit";PreparedStatement preparedStatement = connection.prepareStatement(sql);//5.执行查询 返回结果集ResultSet resultSet = preparedStatement.executeQuery();//6.解析结果集List<Fruit> fruitList=newArrayList<>();//resultSet.next()返回的是一个布尔值//第一层循环返回的是第一行while(resultSet.next()){//1表示读取当前行的第一列的数据//getInt 因为这一列是int类型,所以使用getInt//所以这次循环得到的就是第一行的第一列//放编号 和列名都是可以的(结果集的列名 有别名加别名)int fid = resultSet.getInt(1);String fname = resultSet.getString(2);int price = resultSet.getInt(3);int fcount = resultSet.getInt(4);String remark = resultSet.getString(5);Fruit fruit =newFruit(fid, fname, price, fcount, remark);
            fruitList.add(fruit);}
        resultSet.close();
        preparedStatement.close();
        connection.close();
        fruitList.forEach(System.out::println);}

查询指定的数据:查询一条数据就不用List了,直接用实体类对象就OK
这里用了集合,不用的话去掉集合声明,直接输出实体类对象

publicstaticvoidmain(String[] args)throwsClassNotFoundException,SQLException{Class.forName("com.mysql.cj.jdbc.Driver");Connection connection =DriverManager.getConnection("jdbc:mysql://localhost:3306/fruitdb?user=root&password=0630");String sql="select fid,fname,price,fcount,remark from t_fruit where fid=?";PreparedStatement preparedStatement = connection.prepareStatement(sql);
        preparedStatement.setInt(1,2);List<Fruit> fruitList=newArrayList<>();ResultSet resultSet = preparedStatement.executeQuery();if(resultSet.next()){String fidStr = resultSet.getString("fid");Integer fid =Integer.parseInt(fidStr);String fname = resultSet.getString("fname");String priceStr = resultSet.getString("price");Integer price =Integer.parseInt(priceStr);String fcountStr = resultSet.getString("fcount");Integer fcount=Integer.parseInt(fcountStr);String remark = resultSet.getString("remark");//不要集合 直接在这里输出也可以 只有一条记录Fruit fruit =newFruit(fid, fname, price, fcount, remark);
            fruitList.add(fruit);}
        fruitList.forEach(System.out::println);
        resultSet.close();
        preparedStatement.close();
        connection.close();}

查询总记录条数:结果集就只有一行一列

publicstaticvoidmain(String[] args)throwsClassNotFoundException,SQLException{Class.forName("com.mysql.cj.jdbc.Driver");Connection connection =DriverManager.getConnection("jdbc:mysql://localhost:3306/fruitdb?user=root&password=0630");String sql="select count(fid) from t_fruit";PreparedStatement preparedStatement = connection.prepareStatement(sql);//这个结果集只有一行一列ResultSet resultSet = preparedStatement.executeQuery();if(resultSet.next()){int anInt = resultSet.getInt(1);System.out.println(anInt);}
        resultSet.close();
        preparedStatement.close();
        connection.close();}

2.1通过PreparedStatement解决Statement的问题

在这里插入图片描述

Statement使用字符串拼接的方式,会有SQL注入的问题。使用PreparedStatement。
面试题: 如何避免SQL注入?
1.使用PreparedStatement
2.使用正则表达式过滤传入的参数
3.字符串过滤
4.JSP中调用该函数检查是否包非法字符
5.JSP页面判断代码

2.2获取自增长键值

为什么要获得自增长的主键值,当主表添加数据的时候,主键自增长了。从表要添加新数据的时候,外键和主表的主键相关联,此时需要知道主表自增长的主键值是什么,就需要将自增长的主键值回显。

如何解决?在第四步创建预处理命令对象PreparedStatement时传入第二个参数Statement.RETURN_GENERATED_KEYS,告知SQL取数据的时候将自增长的主键值带回来,以后要用

代码:只有在插入的时候进行主键回显,判断一下SQL语句是以INSERT开始,使用主键回显

protectedintexecuteUpdate(String sql,Object... params){boolean insertFlag=false;
        insertFlag=sql.trim().toUpperCase().startsWith("INSERT");try{
            connection=getConnection();if(insertFlag){
                connection.prepareStatement(sql,Statement.RETURN_GENERATED_KEYS);}else{
                preparedStatement=connection.prepareStatement(sql);}setParams(preparedStatement,params);int count= preparedStatement.executeUpdate();
            resultSet= preparedStatement.getGeneratedKeys();if(resultSet.next()){return((Long)resultSet.getLong(1)).intValue();}return count;}catch(SQLException e){
            e.printStackTrace();}finally{close(resultSet,preparedStatement,connection);}return0;}

2.3批处理

为了加快插入的速度,设置URL属性rewriteBatchedStatement=true
原理:将插入的数据统一追加到values后面,一批添加

publicstaticvoidmain(String[] args)throwsClassNotFoundException,SQLException{//1.加载驱动Class.forName("com.mysql.cj.jdbc.Driver");//2.通过驱动管理器获取连接对象 如果要执行批处理任务  需要添加一个参数 rewriteBatchedStatement=trueConnection connection =DriverManager.getConnection("jdbc:mysql://localhost:3306/fruitdb?rewriteBatchedStatement=true&user=root&password=0630");//3.编写SQL语句String sql="insert into t_fruit values(0,?,?,?,?)";//4.创建预处理命令对象PreparedStatement preparedStatement = connection.prepareStatement(sql);//5.填充参数for(int i =0; i <10; i++){
            preparedStatement.setString(1,"榴莲"+i);
            preparedStatement.setString(2,"15");
            preparedStatement.setString(3,"100");
            preparedStatement.setString(4,"榴莲是一种神奇的水果");//追加到values 追加 放到一批处理
            preparedStatement.addBatch();//如果任务较多 可以分批次执行 每次执行完 清空任务队列if(i%1000==0){
                preparedStatement.executeBatch();
                preparedStatement.clearBatch();}}//6.执行更新(增删改),返回影响行数//剩下的批处理用这条执行int[] count = preparedStatement.executeBatch();System.out.println(Arrays.toString(count));//7.释放资源
        preparedStatement.close();
        connection.close();}

2.4事务

数据库事务就是一种SQL语句执行的缓存机制,不会单条执行完毕就更新数据库数据,最终根据缓存内的多条语句执行结果统一判定。
一个事务内所有语句都成功及事务成功,我们可以触发commit提交事务来结束事务,更新数据。
一个事务内任意一条语句失败,及事务失败,我们可以触发rollback回滚结束事务,数据回到事务之前状态。
事务的ACID特性

  1. 原子性(Atomicity)原子性是指事务是一个不可分割的工作单位,事务中的操作要么都发生,要么都不发生。
  2. 一致性(Consistency)事务必须使数据库从一个一致性状态变换到另外一个一致性状态。
  3. 隔离性(Isolation)事务的隔离性是指一个事务的执行不能被其他事务干扰,即一个事务内部的操作及使用的数据对并发的其他事务是隔离的,并发执行的各个事务之间不能互相干扰。
  4. 持久性(Durability)持久性是指一个事务一旦被提交,它对数据库中数据的改变就是永久性的,接下来的其他操作和数据库故障不应该对其有任何影响。
  • 第三章 数据库连接池—Druid数据源连接技术

连接Connection用的时候创建,用完了再销毁太过浪费。使用数据源连接技术,提供一个连接池,里面存放连接,使用的时候从连接池取,使用完后放回连接池。

在这里插入图片描述

步骤:
1.导入jar
2.硬编码方式和软编码方式(推荐)

硬编码连接方式 代码:

publicstaticvoidmain(String[] args)throwsSQLException{DruidDataSource dataSource =newDruidDataSource();
        dataSource.setDriverClassName("com.mysql.cj.jdbc.Driver");
        dataSource.setUrl("jdbc:mysql://localhost:3306/fruitdb?user=root&password=0630");Connection connection = dataSource.getConnection();System.out.println(connection);//1.被close()的连接对象,并没有真正关闭,而是将状态重新设置为空闲状态,然后放回池中。这样下次获取连接对象,这个对象可以被重复使用//2.没有被close()的连接对象会被一直被占用}

软编码连接方式 代码:
首先要提供一个配置文件:里面的key是固定的

driverClassName=com.mysql.cj.jdbc.Driver
url=jdbc:mysql://localhost:3306/fruitdb
username=root
password=0630
initialSize=2
maxActive=5
maxWait=5000

使用Druid工厂创建连接池:
Properties读的是输入流,使用当前类的类加载器将配置文件变成一个输入流,再使用Properties对象加载,就能获取到配置文件的key-value

publicstaticvoidmain(String[] args)throwsException{//切换jar包修改配置文件就可以了Properties properties =newProperties();//类加载器InputStream resourceAsStream =DemoDruid2.class.getClassLoader().getResourceAsStream("jdbc2.properties");
        properties.load(resourceAsStream);//key是固定的DataSource dataSource=DruidDataSourceFactory.createDataSource(properties);Connection connection = dataSource.getConnection();System.out.println(connection);}
  • 第四章 代码封装

DAO(Data Access Object数据访问对象)层是用来操作数据库的,要有一个DAO接口来规范:

表中的一条记录就对应实体类的一个对象。所有的记录放在List中,即List中的数据就是一个一个的Fruit对象。

publicinterfaceFruitDAO{/**
     * 查询库存列表
     * @return
     */List<Fruit>getFruitList();/**
     * 新增库存
     */booleanaddFruit(Fruit fruit);/**
     * 修改库存
     */booleanupdateFruit(Fruit fruit);/**
     * 根据名称查询指定库存
     */FruitgetFruitByFname(String fname);/**
     * 删除特定库存记录
     */booleandelFruit(String fname);}

未封装前的代码:
实现类:实现的是上面DAO接口

publicclassFruitDaoImplimplementsFruitDAO{Connection connection;PreparedStatement preparedStatement;ResultSet resultSet;finalString DRIVER="com.mysql.cj.jdbc.Driver";finalString URL="jdbc:mysql://localhost:3306/fruitdb?user=root&password=0630";@OverridepublicList<Fruit>getFruitList(){List<Fruit> fruitList=newArrayList<>();try{Class.forName(DRIVER);
            connection =DriverManager.getConnection(URL);String sql="select * from t_fruit";
            preparedStatement = connection.prepareStatement(sql);
            resultSet = preparedStatement.executeQuery();//解析结果集while(resultSet.next()){int fid=resultSet.getInt(1);String fname=resultSet.getString(2);int price=resultSet.getInt(3);int fcount=resultSet.getInt(4);String remark=resultSet.getString(5);Fruit fruit =newFruit(fid, fname, price, fcount, remark);
                fruitList.add(fruit);}}catch(Exception e){thrownewRuntimeException(e);}finally{try{if(resultSet!=null){
                    resultSet.close();}if(preparedStatement!=null){
                    preparedStatement.close();}if(connection!=null&&!connection.isClosed()){
                    connection.close();}}catch(SQLException e){thrownewRuntimeException(e);}}return fruitList;}@OverridepublicbooleanaddFruit(Fruit fruit){try{Class.forName(DRIVER);
            connection=DriverManager.getConnection(URL);String sql="insert into t_fruit values(0,?,?,?,?)";
            preparedStatement=connection.prepareStatement(sql);
            preparedStatement.setString(1,fruit.getFname());
            preparedStatement.setInt(2,fruit.getPrice());
            preparedStatement.setInt(3,fruit.getFcount());
            preparedStatement.setString(4,fruit.getRemark());return preparedStatement.executeUpdate()>0;}catch(ClassNotFoundException e){thrownewRuntimeException(e);}catch(SQLException e){thrownewRuntimeException(e);}finally{try{if(preparedStatement!=null){
                    preparedStatement.close();}if(connection!=null&&!connection.isClosed()){
                    connection.close();}}catch(SQLException e){thrownewRuntimeException(e);}}}@OverridepublicbooleanupdateFruit(Fruit fruit){try{Class.forName(DRIVER);
            connection=DriverManager.getConnection(URL);String sql="update t_fruit set fcount=? where fid=?";
            preparedStatement=connection.prepareStatement(sql);
            preparedStatement.setInt(1,fruit.getFcount());
            preparedStatement.setInt(2,fruit.getFid());return preparedStatement.executeUpdate()>0;}catch(ClassNotFoundException e){thrownewRuntimeException(e);}catch(SQLException e){thrownewRuntimeException(e);}finally{try{if(resultSet!=null){
                    resultSet.close();}if(preparedStatement!=null){
                    preparedStatement.close();}if(connection!=null&&!connection.isClosed()){
                    connection.close();}}catch(SQLException e){thrownewRuntimeException(e);}}}@OverridepublicFruitgetFruitByFname(String fname){try{Class.forName(DRIVER);
            connection=DriverManager.getConnection(URL);String sql="select * from t_fruit where fname like ?";
            preparedStatement=connection.prepareStatement(sql);
            preparedStatement.setString(1,fname);
            resultSet = preparedStatement.executeQuery();if(resultSet.next()){int fid=resultSet.getInt(1);int price=resultSet.getInt(3);int fcount=resultSet.getInt(4);String remark=resultSet.getString(5);returnnewFruit(fid,fname,price,fcount,remark);}}catch(ClassNotFoundException|SQLException e){thrownewRuntimeException(e);}finally{try{
                preparedStatement.close();
                connection.close();}catch(SQLException e){thrownewRuntimeException(e);}}returnnull;}@OverridepublicbooleandelFruit(String fname){try{Class.forName(DRIVER);
            connection=DriverManager.getConnection(URL);String sql="delete from t_fruit where fname like ?";
            preparedStatement=connection.prepareStatement(sql);
            preparedStatement.setString(1,fname);return preparedStatement.executeUpdate()>0;}catch(ClassNotFoundException e){thrownewRuntimeException(e);}catch(SQLException e){thrownewRuntimeException(e);}finally{try{if(preparedStatement!=null){
                    preparedStatement.close();}if(connection!=null&&!connection.isClosed()){
                    connection.close();}}catch(SQLException e){thrownewRuntimeException(e);}}}}

对代码进行封装:

查询中:要先设法获取到泛型的类型,是Fruit。拿到泛型的类型后,通过反射创建一个实例,得到fruit对象。每取出一行一列的数据,给fruit对象赋值,然后将这个fruit对象追加到list中。

publicabstractclassBaseDAO<T>{publicfinalString DRIVER="com.mysql.cj.jdbc.Driver";publicfinalString URL="jdbc:mysql://localhost:3306/fruitdb?user=root&password=0630";protectedConnection connection;protectedPreparedStatement preparedStatement;protectedResultSet resultSet;/**
     * 获取T的Class对象
     * 怎么获取?
     */privateClass entityClass;publicBaseDAO(){//getClass()获取实现类(FruitDAOImpl)的Class,创建的是FruitDAOImpl的实例//那么子类构造方法内部首先会调用父类BaseDAO的无参构造方法//因此此处的getClass()会执行,但是getClass获取的是FruitDAOImpl的Class//getGenericSuperclass()获取的是BaseDAO的ClassType genericType=getClass().getGenericSuperclass();//ParameterizedType参数化类型  获取实际的类型参数  实际传入的类型是什么 就可以获取到Type[] actualTypeArguments =((ParameterizedType) genericType).getActualTypeArguments();//获取到的<T>中的T的真实的类型Type actualType = actualTypeArguments[0];try{//得到泛型的类型名 就是Fruit
            entityClass=Class.forName(actualType.getTypeName());}catch(ClassNotFoundException e){thrownewRuntimeException(e);}}protectedConnectiongetConnection(){try{Class.forName(DRIVER);returnDriverManager.getConnection(URL);}catch(ClassNotFoundException e){
            e.printStackTrace();}catch(SQLException e){
            e.printStackTrace();}returnnull;}protectedvoidclose(ResultSet resultSet,PreparedStatement preparedStatement,Connection connection){try{if(resultSet!=null){
                resultSet.close();}if(preparedStatement!=null){
                preparedStatement.close();}if(connection!=null&&!connection.isClosed()){
                connection.close();}}catch(SQLException e){thrownewRuntimeException(e);}}/**
     * 给预处理命令对象设置参数
     * @param preparedStatement
     * @param params
     * @throws SQLException
     */privatevoidsetParams(PreparedStatement preparedStatement,Object... params)throwsSQLException{if(params!=null&&params.length>0){for(int i =0; i < params.length; i++){
                preparedStatement.setObject(i+1,params[i]);}}}/**
     * 执行更新,返回影响行数
     */protectedintexecuteUpdate(String sql,Object... params){boolean insertFlag=false;
        insertFlag=sql.trim().toUpperCase().startsWith("INSERT");try{
            connection=getConnection();if(insertFlag){
                connection.prepareStatement(sql,Statement.RETURN_GENERATED_KEYS);}else{
                preparedStatement=connection.prepareStatement(sql);}setParams(preparedStatement,params);int count= preparedStatement.executeUpdate();
            resultSet= preparedStatement.getGeneratedKeys();if(resultSet.next()){return((Long)resultSet.getLong(1)).intValue();}return count;}catch(SQLException e){
            e.printStackTrace();}finally{close(resultSet,preparedStatement,connection);}return0;}/**
     * 通过反射技术给obj对象的property属性赋propertyValue值
     */privatevoidsetValue(Object obj,String property,Object propertyValue){Class clazz = obj.getClass();try{//获取property这个字符串对应的属性名,比如"fid"去找obj对象中的fid属性Field field = clazz.getDeclaredField(property);if(field!=null){
                field.setAccessible(true);//propertyValue值赋给obj对象的属性
                field.set(obj,propertyValue);}}catch(NoSuchFieldException e){thrownewRuntimeException(e);}catch(IllegalAccessException e){thrownewRuntimeException(e);}}/**
     * 执行查询:返回的是List
     */protectedList<T>executeQuery(String sql,Object... params){List<T> list=newArrayList<>();try{
            connection =getConnection();
            preparedStatement = connection.prepareStatement(sql);setParams(preparedStatement,params);//保存的是行数据
            resultSet = preparedStatement.executeQuery();//获取结果集的元数据//元数据:描述结果集数据的数据,就是这个结果集有那些列、什么类型等等ResultSetMetaData metaData = resultSet.getMetaData();int count = metaData.getColumnCount();//解析结果集while(resultSet.next()){//得到fruit对象T entity=(T) entityClass.newInstance();//第一行  第一列  第二列  第三列...for(int i =0; i < count; i++){//得到列名String columnName = metaData.getColumnName(i +1);//得到列的值Object  columnValue = resultSet.getObject(i +1);setValue(entity,columnName,columnValue);}
               list.add(entity);}}catch(SQLException e){
            e.printStackTrace();}catch(InstantiationException e){thrownewRuntimeException(e);}catch(IllegalAccessException e){thrownewRuntimeException(e);}finally{close(resultSet,preparedStatement,connection);}return list;}/**
     * 执行查询 返回单个实体对象
     */protectedTload(String sql,Object... params){try{
            connection =getConnection();
            preparedStatement = connection.prepareStatement(sql);setParams(preparedStatement,params);//保存的是行数据
            resultSet = preparedStatement.executeQuery();//获取结果集的元数据//元数据:描述结果集数据的数据,就是这个结果集有那些列、什么类型等等ResultSetMetaData metaData = resultSet.getMetaData();int count = metaData.getColumnCount();//解析结果集if(resultSet.next()){//得到fruit对象T entity=(T) entityClass.newInstance();//第一行  第一列  第二列  第三列...for(int i =0; i < count; i++){//得到列名String columnName = metaData.getColumnName(i +1);//得到列的值Object  columnValue = resultSet.getObject(i +1);setValue(entity,columnName,columnValue);}return entity;}}catch(SQLException e){
            e.printStackTrace();}catch(InstantiationException e){thrownewRuntimeException(e);}catch(IllegalAccessException e){thrownewRuntimeException(e);}finally{close(resultSet,preparedStatement,connection);}returnnull;}/**
     * 执行复杂查询,返回例如统计结果 行和列所有的值
     */protectedObject[]executeComplexQuery(String sql,Object...params){try{
            connection =getConnection();
            preparedStatement = connection.prepareStatement(sql);setParams(preparedStatement,params);//保存的是行数据
            resultSet = preparedStatement.executeQuery();//获取结果集的元数据//元数据:描述结果集数据的数据,就是这个结果集有那些列、什么类型等等ResultSetMetaData metaData = resultSet.getMetaData();int count = metaData.getColumnCount();Object[] columnValueArr=newObject[count];//解析结果集if(resultSet.next()){//第一行  第一列  第二列  第三列...for(int i =0; i < count; i++){//得到列的值Object  columnValue = resultSet.getObject(i +1);
                    columnValueArr[i]=columnValue;}return columnValueArr;}}catch(SQLException e){
            e.printStackTrace();}finally{close(resultSet,preparedStatement,connection);}returnnull;}}

实现类中:只需要提供SQL语句、调用方法即可

publicclassFruitDaoImplextendsBaseDAO<Fruit>implementsFruitDAO{@OverridepublicList<Fruit>getFruitList(){String sql="select * from t_fruit";returnsuper.executeQuery(sql);}@OverridepublicbooleanaddFruit(Fruit fruit){String sql="insert into t_fruit values(0,?,?,?,?)";//insert语句返回的是自增列的值 而不是影响行数 自增主键回显int count =super.executeUpdate(sql,fruit.getFname(),fruit.getPrice(),fruit.getFcount(),fruit.getRemark());System.out.println(count);return count>0;}@OverridepublicbooleanupdateFruit(Fruit fruit){String sql="update t_fruit set fcount=? where fid=?";returnsuper.executeUpdate(sql,fruit.getFcount(),fruit.getFid())>0;}@OverridepublicFruitgetFruitByFname(String fname){String sql="select * from t_fruit where fname like ?";returnsuper.load(sql,fname);}@OverridepublicbooleandelFruit(String fname){String sql="delete from t_fruit where fname like ?";//影响行数大于0就表示删除成功了returnsuper.executeUpdate(sql,fname)>0;}}
标签: java 数据库 mysql

本文转载自: https://blog.csdn.net/weixin_45703331/article/details/129801850
版权归原作者 莫听穿林打叶声@ 所有, 如有侵权,请联系我们删除。

“JDBC---Java连接数据库”的评论:

还没有评论