日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 运维知识 > 数据库 >内容正文

数据库

【Java学习笔记】 MYSQL03 学习使用JDBC访问数据 以及 JDBC的优化和封装

發布時間:2023/12/20 数据库 32 豆豆
生活随笔 收集整理的這篇文章主要介紹了 【Java学习笔记】 MYSQL03 学习使用JDBC访问数据 以及 JDBC的优化和封装 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

通過JDBC 訪問數據

學習時間 7月11日

一、使用Java訪問數據庫

JAVA 主動 提出接口 ,各種數據庫適應 這些接口

  • 接口就是 JDBC Java Database Connector
  • 各種數據庫都會提供一套對應的驅動程序(JAR文件
  • 即不同的數據庫都有自己對應的JAR文件

1、導入mysql對應的JAR包

  • 創建lib文件夾
  • 將jar文件放入
  • 右鍵jar包,點擊 add as library導入包
  • 2、訪問數據庫的步驟

  • 加載驅動:涉及到反射

    • Class.forName 需要捕獲異常
      • 快速添加異常的快捷鍵Alt + 回車,選第二個
  • 連接數據庫:查找db文件

    • 配置url :jdbc:mysql://127.0.0.1:3306/zy_sys?useUnicode=true&characterEncoding=UTF-8&useSSL=false

      ip地址,數據庫名字,編碼unicode,不使用加密

      • zy_sys對應的是數據庫名稱
    • 創建連接 :Connection connection = DriverManager.getConnection(url , user , password);

      • 也需要異常捕獲
  • SQL語句

    • 創建一個字符串存儲 SQL語句
    • 建議先在DBMS中測試一次
  • 預編譯SQL語句(判斷語法錯誤,獲取執行的對象)

    • 固定語法:PreparedStatement preparedStatement = connection.prepareStatement(sql);
  • 執行操作

  • 獲取執行結果

    • 增刪改調用方法executeUpdate():

      • 返回類型int 表示受影響的條數
      • 獲取執行結果只需要輸出這個返回值即可
    • 查找調用方法executeQuery():

      • 返回值類型是ResultSet(結果集:類似對象列表)

      • 用 while 循環 遍歷結果集.

        用到ResultSet.next()方法——向下移動一行,返回布爾值。默認是在空行,next一行才是第一行。舉個例子如下:

        while (resultSet.next()){// 使用對應的方法獲得相應的數據類型String sno = resultSet.getString("sno");String sname = resultSet.getString("sname");int sage = resultSet.getInt("sage");// 按順序輸出結果即可System.out.println(sno + "\t" + sname + " \t" + sage);}
  • 關閉操作(關閉連接,關閉接口,關閉對象) 釋放資源

    • 關閉順序有大小之分,小的先關,大的后關
  • 3、舉個例子(增刪改

    package com.cykj.demo;import java.sql.Connection; import java.sql.DriverManager; import java.sql.SQLException;public class Test {public static void main(String[] args) {try {// 1、加載驅動 ——涉及到反射知識點Class.forName("com.mysql.jdbc.Driver"); // Driver類 驅動String url = "jdbc:mysql://127.0.0.1:3306/zy_sys?useUnicode=true&characterEncoding=UTF-8&useSSL=false";// 2、連接數據庫String user = "root"; // 賬號String password = "root"; // 密碼Connection connection = DriverManager.getConnection(url , user , password); // 創建連接System.out.println("連接成功!");// 3、寫SQL語句String sql = "INSERT INTO zy_student(sno,sname,ssex) VALUES ('jx220501','老王',1)";// 4、預編譯PreparedStatement preparedStatement = connection.prepareStatement(sql);// 5、執行操作int re = preparedStatement.executeUpdate();// sql的增刪改都用executeUpdate() 返回類型int 表示受影響的條數// 6、獲取執行結果System.out.println(re);// 7、關閉preparedStatement.close(); // 關閉編譯connection.close(); // 關閉連接// 關閉順序有大小之分,小的先關,大的后關} catch (ClassNotFoundException e) {e.printStackTrace();} catch (SQLException e) {e.printStackTrace();}} }

    4、 查找例子

    package com.cykj.demo;import java.sql.*;public class Test2 {public static void main(String[] args) {try {// 1、加載驅動 ——涉及到反射知識點Class.forName("com.mysql.jdbc.Driver"); // Driver類 驅動// 2、連接數據庫String url = "jdbc:mysql://127.0.0.1:3306/zy_sys?useUnicode=true&characterEncoding=UTF-8&useSSL=false";String user = "root"; // 賬號String password = "root"; // 密碼Connection connection = DriverManager.getConnection(url , user , password); // 創建連接System.out.println("連接成功!");// 3、寫SQL語句String sql = "SELECT sno,sname,sage FROM zy_student WHERE sno LIKE 'AF%';";// 4、預編譯PreparedStatement preparedStatement = connection.prepareStatement(sql);// 5、執行操作ResultSet resultSet = preparedStatement.executeQuery(); // 查找數據庫用的是executeQuery()// 6、獲取執行結果while (resultSet.next()){// 使用對應的方法獲得相應的數據類型String sno = resultSet.getString("sno"); String sname = resultSet.getString("sname");int sage = resultSet.getInt("sage");// 按順序輸出結果即可System.out.println(sno + "\t" + sname + " \t" + sage);}// 7、關閉resultSet.close();preparedStatement.close(); // 關閉編譯connection.close(); // 關閉連接// 關閉順序有大小之分,小的先關,大的后關} catch (ClassNotFoundException e) {e.printStackTrace();} catch (SQLException e) {e.printStackTrace();}} }===輸出結果=== AF121101 小王 22 AF121102 小紅 22 AF121103 王思思 23 AF121104 小灰 30 AF121105 小林 27 AF121106 小張 26 AF121107 小麗 32 AF121108 小花 29 AF121109 小馬 26

    JDBC優化

    一、在預編譯時拼接字符串

    • SQL語句的拼接,有什么缺點?

      • 寫法麻煩
      • 不安全,留有SQL注入的風險
    • 如何解決呢?

      用問號?替代字符串中需要拼接的位置

      • 預編譯時加入字符串,舉個例子
      // 原字符串 String sql = "SELECT * FROM tb_user WHERE userid = '" + useridText + "' OR username = '" + useridText + "'";
      • 修改后
      // 用問號替代拼接的字符串 意思類似挖坑 String sql = "SELECT * FROM tb_user WHERE userid = ? OR username = ?";; ps = connection.prepareStatement(sql); // 預編譯 // 利用setString()方法 插入字符串,計數從1開始 ps.setString(1,useridText); ps.setString(2,useridText);
      • 簡單理解:這種方法類似挖坑和填坑
      • 先挖坑:用問號?替代也要拼接的字符串
      • 再填坑,利用setString()方法 插入字符串,計數從1開始
      • 注意:setString會自動給這個字符串加入單引號,無需再添加

    二、優化關閉操作

    • 在JDBC操作中,如果編譯出現報錯,后續的關閉操作就不再執行了。這樣會導致數據庫負擔較大

      • 要如何解決該問題呢?
        • 利用異常關鍵字finally的特點:異常處理中finally是最后必須執行一次的,可以把關閉操作寫在這里!
    • 具體操作如下

    • 將需要關閉的對象,設置為全局變量

    • 目標**:在finally語句塊里關閉對象**

    • 關閉時也要加入異常捕獲,注意:每次關閉都要分別捕獲異常

    • 在關閉前,也要加入一個if判斷,判斷對象不等于null,才進行關閉操作。舉個例子

      try{。。。 } catch{。。。 } finally {try {if (connection != null){ // 判斷連接是否為空connection.close(); // 關閉連接}} catch (SQLException e) { // 加入關閉操作的異常捕獲e.printStackTrace();}try {if (ps != null) {ps.close();}} catch (SQLException e) {e.printStackTrace();} }

    三、封裝

    經過觀察發現,1、2、7三步的基本類似,可以偷懶共同的方法,可以封裝起來,甚至寫成一個類,即:

    共同的代碼———> 方法 ———> 類

    1、2、7三步的代碼 ———> 分別封裝成方法 ———> 放在同一個類中(工具層)

    • 這種類存放在工具層,這個類就成為"工具包"

    1、 工具類 Utils

    • 用于存放各種封裝起來的方法,提供給其他模塊調用

    2、封裝第一步和第二步 加載驅動建立連接

    • 封裝1+2步

      public Connection getConnection (){try {// 1、加載驅動Class.forName("com.mysql.jdbc.Driver");String url = "jdbc:mysql://127.0.0.1:3306/goods_db?" +"useUnicode=true&" +"characterEncoding=UTF-8&useSSL=false";String user = "root";String password = "root";// 2、建立連接Connection connection = DriverManager.getConnection(url,user,password);return connection; // 連接成功則返回連接} catch (ClassNotFoundException e) {e.printStackTrace();} catch (SQLException e) {e.printStackTrace();}return null; // 連接失敗則返回空 }
    • 但是存在一個問題,URL,用戶名,密碼都是不固定的,這時候就需要用到配置文件*.properties” 、 xml 或 yml

      • 如何使用配置文件?

    3、properties配置文件的使用

    • 鍵值對格式 : key=value

      • 注意:等號的兩邊都不能有空格
    • 具體使用步驟

    • 將配置文件 拷貝到 項目工程目錄 下

    • 讀取配置文件的值

      • 要有對應的庫 ——> 找到對應的或對象 ——> 方法

      • Java有對應的類 Properties,實現的思路如下:

      • 讀取文件 調用InputStream類 (IO流的內容 后續會接觸到
      • 實例化屬性類 Properties
      • 調用load(文件名)加載文件
      • 取值 用getProperty(鍵名)來搜索對應的數據,返回值類型為String
      • 舉個例子

        public static void main(String[] args) {try {// 用IO讀取文件InputStream inputStream = new FileInputStream("db.properties");// 加載Properties pps = new Properties();pps.load(inputStream);// 獲取字符串String driver = pps.getProperty("driver");System.out.println(driver);} catch (FileNotFoundException e) {e.printStackTrace();} catch (IOException e) {e.printStackTrace();} }
    • 在工具類中,獲取對應的驅動,url,用戶名,密碼存放在String

    • 在執行連接數據庫時,直接調用這些字符串進行登陸即可


    • 在實際應用場景中,只需要讀取一次配置文件。那么,如何只讀取一次配置文件?
      • 構造函數?實例化的時候只運行一次,但是多次實例化還會再次執行
      • 這里就需要用到靜態代碼塊——
        • 語法:static {代碼塊}
        • 在類里的靜態代碼塊,只會執行一次
        • 執行的時間是在構造函數之前,且需要實例化的時候才會運行

    4、封裝第七步:關閉操作

    • 舉個例子

      public void closeJdbc(Connection con , PreparedStatement ps , ResultSet rs){try {if (rs != null){rs.close();}} catch (SQLException e) {e.printStackTrace();}try {if (con != null){ // 判斷連接是否為空con.close(); // 關閉連接}} catch (SQLException e) { // 加入關閉操作的異常捕獲e.printStackTrace();}try {if (ps != null) {ps.close();}} catch (SQLException e) {e.printStackTrace();} }

    5、調用思路

    • 思路如下:

    • 先將工具類實例化為全局變量 (所有需要關閉的對象也要聲明為全局變量)
    • 調用工具類的方法 getConnection () 獲取 連接 Connection
      • 對應的完成了第一步和第二步
    • 繼續完成 寫SQL語句 預編譯 執行和獲取結果的步驟
    • 在最后的finally的語句塊中調用關閉的方法closeJdbc(),關閉掉對應的對象。
      • 由于關閉方法有多個對象,當不存在某個對象時,可以傳入null

    6、工具類的具體案例

    • 舉個例子

      Connection connection = null; PreparedStatement ps = null; ResultSet resultSet = null; JdbcUtils jdbcUtils = new JdbcUtils(); connection = jdbcUtils.getConnection(); // 調用方法獲得連接 try {String sql = "SELECT * FROM tb_user WHERE userid = ? OR username = ?"; // 預編譯ps = connection.prepareStatement(sql);ps.setString(1, useridText);ps.setString(2, usernameText);resultSet = ps.executeQuery();if (resultSet.next()) {JOptionPane.showMessageDialog(null, "賬號已重復!","注意", JOptionPane.WARNING_MESSAGE);return;} else {// 賬號沒有重復 可以繼續執行操作 。。。} } catch (SQLException e) {e.printStackTrace(); } finally {jdbcUtils.closeJdbc(connection, ps, resultSet);// 如果沒有resultset,就傳入null即可 }

    總結

    以上是生活随笔為你收集整理的【Java学习笔记】 MYSQL03 学习使用JDBC访问数据 以及 JDBC的优化和封装的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。