JdbcTemplate的使用


NamedParameterJdbcTemplate中包含了一個JdbcTemplateNamedParameterJdbcTemplate中的很多方法實際上還是交由JdbcTemplate去完成。NamedParameterJdbcTemplateJdbcTemplate增加的功能是對輸入的條件參數取別名。例如:

String sql2 = "select id,tname as name,tpwd as password from tadd where tname = :name";將查詢參數中數據庫的列名tname換成了name

 

SimpleJdbcTemplate中包含了一個NamedParameterJdbcTemplateSimpleJdbcTemplate中的很多實現是交由了底層的JdbcTemplate去完成。SimpleJdbcTemplate所增強的功能是泛型和可變長度的參數。

Spring 3.1版本之后,NamedParameterJdbcTemplateJdbcTemplate也支持了泛型,SimpleJdbcTemplate就被標注為了過時。但是在Spring 3.1版本之前,能使用SimpleJdbcTemplate還是要使用SimpleJdbcTemplate

 

SimpleJdbcTemplate中的主要方法如下:

  mysql> desc tadd; 

  +-------+------------------------+--------+--------+-------------+------------------------------------+

  | Field | Type                                | Null     | Key        | Default        | Extra                            |

  +-------+----------------------+-----------+--------+--------------+-----------------------------------+

  | id     | bigint(255)          | NO          | PRI        |                     | auto_increment                      |

  | tname | varchar(300)                | YES        |               | NULL         |                                   |

  | tpwd  | varchar(300) | YES      |                 | NULL    |              |                                                               |

  +-----------+--------------------+---------+--------+---------------+-----------------------------------+

  mysql> insert into tadd(tname,tpwd) values ('apply','asure');

     

首先來看只返回一條記錄的查詢操作,返回多條記錄將失敗。

    使用queryForObject方法及其重載的方法  

   1. 沒有JavaBean時的操作,使用queryForObject(String sql, RowMapper<T> rm, Map<String, ?> args)

String sql2 = "select id,tname as name,tpwd as password from tadd where tname = :n";
    RowMapper<UserBean> rw = new RowMapper<UserBean>(){
            @Override
            public UserBean mapRow(ResultSet paramResultSet, int paramInt) throws SQLException {
                UserBean ub = new UserBean();
                ub.setId(paramResultSet.getObject("id") + "");
                ub.setName(paramResultSet.getObject("name") + "");
                ub.setPassword(paramResultSet.getObject("password") + "");
                return ub;
            }
        };
        Map<String, String> map = new HashMap<String, String>();
        map.put("n", "apply");
        UserBean ub = jdbctemplate.queryForObject(sql2, rw, map);

 查詢語句中as后面的名稱是別名,會將查詢結果中數據庫的列名替換為別名。tname = :n條件參數取別名有二個作用,一是可以作用於Map參數,第二個是作用於下面的BeanPropertySqlParameterSource,使用BeanPropertySqlParameterSource時別名要和JavaBean中的名稱一致。

  2.也可以使用可變長度的參數,這時條件參數不能取別名,要使用占位符的形式:

String sql2 = "select id,tname as name,tpwd as password from tadd where tname = ?";
    UserBean ub = jdbctemplate.queryForObject(sql2, rw, "apply");

 

3.創建一個名為UserBeanJavaBean,屬性為idnamepassword,對應屬性有getset方法。

使用方法:T queryForObject(String sql, ParameterizedRowMapper<T> rm, Map<String, ?> args)

UserBean ub = jdbctemplate.queryForObject(sql2new BeanPropertyRowMapper(UserBean.class),map);

可以使用可變長度的參數,這時sql中也同樣條件參數不能取別名:

UserBean ub = jdbctemplate.queryForObject(sql2new BeanPropertyRowMapper(UserBean.class),"apply");

4.還可以將Map參數替換,采用完全的面向對象的方式:

String sql2 = "select id,tname as name,tpwd as password from tadd where tname = :name";

userb.setName("apply");

UserBean ub = jdbctemplate.queryForObject(sql2, new BeanPropertyRowMapper(UserBean.class),new BeanPropertySqlParameterSource(userb));

  注意:使用BeanPropertySqlParameterSource時別名要和JavaBean中的名稱一致,否則會出錯,和第一種情況比較。

5.查詢結果又多條時,可以使用queryqueryForList或者queryForMap,只要弄清楚參數中的ParameterizedRowMapperSqlParameterSource即可。 

查詢結果為基本類型或者String型時,可以使用queryForObject, queryForInt等。

查詢的操作使用各種的query重載方法,增加、刪除、修改的操作使用各種的update重載方法,使用類似。 

還有就是批量修改使用batchUpdate的各種重載方法。     

6. NamedParameterJdbcTemplate中的各方法與SimpleJdbcTemplate類似,可能參數的順序會不太一樣。有下面幾個有用的方法:

  用KeyHolder獲取新插入數據的主鍵值,可以是單一主鍵或者是聯合主鍵。

String sql3 = "insert into tadd(tname) values (:name)";

UserBean userb = new UserBean();

userb.setName("applyee");

KeyHolder kh = new GeneratedKeyHolder();

jdbctemplate.update(sql3, new BeanPropertySqlParameterSource(userb), kh);

userb.setId(kh.getKey().intValue()+ "");

 

7.行映射器ResultSetExtractorRowCallbackHandlerRowMapper

RowMapper前面已經用到,應用起來也最為簡單,只需要處理單行數據即可。

String sql4 = "select id,tname as name,tpwd as password from tadd where id < :id";
RowMapper<UserBean> rw = new RowMapper<UserBean>(){
            @Override
            public UserBean mapRow(ResultSet paramResultSet, int paramInt) throws SQLException {
                UserBean ub = new UserBean();
                ub.setId(paramResultSet.getObject("id") + "");
                ub.setName(paramResultSet.getObject("name") + "");
                ub.setPassword(paramResultSet.getObject("password") + "");
                return ub;
            }
    };
UserBean user = new UserBean();
        user.setId("4");        
List<UserBean> users = jdbctemplate.query(sql4, new BeanPropertySqlParameterSource(user), rw);
        for(UserBean u: users){
            System.out.println(u);
    }

  RowCallbackHandler需要自己處理每行的數據

final List<UserBean> userList = new ArrayList<UserBean>();
        RowCallbackHandler rch = new RowCallbackHandler(){
            @Override
            public void processRow(ResultSet paramResultSet)
                    throws SQLException {
                UserBean ub = new UserBean();
                ub.setId(paramResultSet.getObject("id") + "");
                ub.setName(paramResultSet.getObject("name") + "");
                ub.setPassword(paramResultSet.getObject("password") + "");
                userList.add(ub);
            }
        
        };
        
        UserBean user = new UserBean();
        user.setId("4");        
        jdbctemplate.query(sql4, new BeanPropertySqlParameterSource(user), rch);
        for(UserBean u: userList){
            System.out.println(u);
        }

  ResultSetExtractor也需要自己處理結果集:

ResultSetExtractor rse = new ResultSetExtractor(){
            public Object extractData(ResultSet rs)
                    throws SQLException, DataAccessException {
                List<UserBean> userList = new ArrayList<UserBean>();
                while(rs.next()){
                    UserBean ub = new UserBean();
                    ub.setId(rs.getObject("id") + "");
                    ub.setName(rs.getObject("name") + "");
                    ub.setPassword(rs.getObject("password") + "");
                    userList.add(ub);
                }    
                return userList;
            }            
        };
        
        UserBean user = new UserBean();
        user.setId("4");        
        List<UserBean> ul = jdbctemplate.query(sql4, new BeanPropertySqlParameterSource(user), rse);
        for(UserBean u: ul){
            System.out.println(u);
        }

8.還可以使用回調函數的方式來實現,相當於自己可以使用JDBC重寫代碼,而不是使用封裝好的方法:

sql語句的回調,使用PreparedStatementCallback返回已經編譯好的sql語句再進行處理

test.execute("update xx set name = 'oo' where id= ?",
    new PreparedStatementCallback(){
     public Object doInPreparedStatement(PreparedStatement ps) throws SQLException, DataAccessException {
      ps.setString(1, "123");//這里的參數對應?
      ps.addBatch();
      ps.setString(1, "456");
      ps.addBatch();
      return ps.executeBatch();
     }
  }); 

連接的回調execute(ConnectionCallback<T> action)

 

9. 通過JDBCTemplate操作數據庫,鏈接是不需要手動地關閉的,但是如果從JDBCTemplate中獲取了鏈接則需要手動地去關閉鏈接。

例如,jdbcTemplate.getDataSource().getConnection()就需要自己去關閉數據庫鏈接,否則會導致嚴重的后果。

DataSourceUtils.releaseConnection(con, getDataSource());

 

 

 

 

 

 

 

 

 

 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM