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

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 运维知识 > 数据库 >内容正文

数据库

java数据库编程——执行SQL 语句

發(fā)布時(shí)間:2023/12/3 数据库 30 豆豆
生活随笔 收集整理的這篇文章主要介紹了 java数据库编程——执行SQL 语句 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

【0】README

1) 本文文字描述+source code 均轉(zhuǎn)自 core java volume 2 , 旨在理解 java數(shù)據(jù)庫(kù)編程——執(zhí)行SQL 語(yǔ)句 的基礎(chǔ)知識(shí) ;
2)for source code, please visit : https://github.com/pacosonTang/core-java-volume/tree/master/coreJavaAdvanced/chapter4/executeSQL
3)for database connection config, please visit : https://github.com/pacosonTang/core-java-volume/blob/master/coreJavaAdvanced/chapter4/database.properties


【1】java數(shù)據(jù)庫(kù)編程——執(zhí)行SQL 語(yǔ)句相關(guān)

1)執(zhí)行 SQL 命令前, 首先需要?jiǎng)?chuàng)建一個(gè) Statement 對(duì)象: 要?jiǎng)?chuàng)建 statement 對(duì)象,不需要調(diào)用 DriverManager.getConnection 方法所獲得的 Connection對(duì)象;(干貨——Statement object == 語(yǔ)句對(duì)象)

  • step1) Statement stat = conn.createStatement();
  • step2) 將要執(zhí)行的 SQL 語(yǔ)句放入字符串中,如:

    String command = “update ….”;

  • step3) 然后,調(diào)用Statement 接口中的executeUpdate 方法:

    stat.executeUpdate(command); // executeUpdate 方法:將返回受SQL命令影響的行數(shù), 或者對(duì)于不返回行數(shù)的語(yǔ)句返回0; (干貨——executeUpdate返回受SQL命令影響的行數(shù),或者0)

2)execute系列方法: (干貨——execute系列方法:executeUpdate + executeQuery + execute)

  • 2.1)executeUpdate 方法:既可以執(zhí)行諸如 insert, update, 和 delete之類的操作(DML), 也可以執(zhí)行諸如 create , drop 之類的數(shù)據(jù)定義語(yǔ)句(DDL);
  • 2.2)executeQuery方法: 執(zhí)行 select 查詢語(yǔ)句時(shí) 必須使用 executeQuery 方法;
  • 2.3)execute 方法: 可以執(zhí)行任意的sql 語(yǔ)句, 通常只用于用戶提供的交互式查詢;

3)查詢結(jié)果(ResultSet 類型): executeQuery 方法返回一個(gè)ResultSet類型的對(duì)象, 可以通過(guò)它來(lái)每次一行地迭代遍歷所有查詢結(jié)果;

ResultSet rs = stat.executeQuery(“select * from books”);

  • 3.1)分析結(jié)果集時(shí)通常可以使用類似如下循環(huán)語(yǔ)句的代碼:

    while(rs.next() )
    {
    look at a row of the result set
    }

  • Warnning)

    • W1)ResultSet接口的 迭代協(xié)議與 java.util.Iterator 接口稍有不同。 對(duì)于ResultSet 接口, 迭代器初始化時(shí)被設(shè)定在第一行之前的位置,必須調(diào)用 next 方法將它移動(dòng)到第一行; (干貨——ResultSet接口的 迭代協(xié)議與 java.util.Iterator 接口稍有不同)
    • W2)另外,它沒(méi)有hasNext方法, 我們需要不斷地調(diào)用 next, 直至該方法返回 false;
    • W3)結(jié)果集中行的順序是任意的, 不能為行序強(qiáng)加任何意義; (干貨——ResultSet結(jié)果集中行的順序是任意的, 不能為行序強(qiáng)加任何意義)
  • 3.2)查看每一行,需要知道每一列的內(nèi)容:

    String str = rs.getString(1);
    double price = rs.getDouble(1);

  • 3.3)不同的數(shù)據(jù)類型有不同的訪問(wèn)器: 比如 getString 和 getDouble; 每個(gè)訪問(wèn)器都有兩種形式,一種接收數(shù)字類型參數(shù),一個(gè)接收字符串類型參數(shù);

  • Warning) 數(shù)據(jù)庫(kù)的列序號(hào)從1開(kāi)始算 ;

  • 3.4)當(dāng)使用 字符串參數(shù)時(shí), 指的是結(jié)果集中以該字符串為列名的列;如,
    rs.getDouble(“price”) 返回列名為 Price 的列所對(duì)應(yīng)的值;

  • 3.5)當(dāng)get方法的類型和列的數(shù)據(jù)類型不一致時(shí), 每個(gè)get 方法都會(huì)進(jìn)行合理的類型轉(zhuǎn)換;

【2】管理連接、語(yǔ)句和結(jié)果集

1)每個(gè)Connection對(duì)象都可以創(chuàng)建一個(gè)或多個(gè) Statement對(duì)象;

  • 1.1)同一個(gè)Statement對(duì)象可以用于不相關(guān)的命令和查詢;
  • 1.2)但是,一個(gè)Statement對(duì)象最多只能有一個(gè)打開(kāi)的結(jié)果集;
  • 1.3)需要說(shuō)明的是: 至少有一種常用的數(shù)據(jù)庫(kù)(Microsoft SQL Server) 的JDBC驅(qū)動(dòng)程序只允許同時(shí)存在一個(gè)活動(dòng)的 Statement 對(duì)象。使用 DatabaseMetaData 接口中的 getMaxStatements 方法可以獲取JDBC 驅(qū)動(dòng)程序支持的同時(shí)活動(dòng)的語(yǔ)句對(duì)象的總數(shù);
    • 1.3.1)這看上去很有局限性。實(shí)際上,我們通常并不需要同時(shí)處理多個(gè) 結(jié)果集。對(duì)數(shù)據(jù)庫(kù)進(jìn)行組合查詢比使用 java 程序遍歷多個(gè)結(jié)果集要高效得多; (干貨——我們通常并不需要同時(shí)處理多個(gè) 結(jié)果集,對(duì)數(shù)據(jù)庫(kù)進(jìn)行組合查詢比使用 java 程序遍歷多個(gè)結(jié)果集要高效得多)
  • 1.4)close方法:使用完 ResultSet , Statement , Connection對(duì)象后,立即調(diào)用 close方法;
  • 1.5)closeOnCompletion方法: 在java 7中, 可以在 Statement 上調(diào)用 closeOnCompletion 方法, 在其所有結(jié)果集都被關(guān)閉后, 該語(yǔ)句會(huì)立即被自動(dòng)關(guān)閉; (干貨——java7引入的新方法closeOnCompletion)
  • 1.6)如果所用連接都是短時(shí)的,無(wú)需考慮關(guān)閉語(yǔ)句和結(jié)果集。 只需要將 close 語(yǔ)句放 在 帶資源的try語(yǔ)句中, 以便確保最終連接對(duì)象不可能繼續(xù)保持打開(kāi)狀態(tài):

    try (Connnection conn =…)
    {
    Statement stat = conn.createStatement();
    ResultSet result = stat.executeQuery(queryStr);
    process query result
    }

Attention) 應(yīng)該使用帶資源的try 語(yǔ)句塊來(lái)關(guān)閉連接,并使用一個(gè)單獨(dú)的 try /catch 塊處理異常。 分離 try 程序塊可以 提高代碼的可讀性和可維護(hù)性;


【3】分析 SQL 異常(SQLException)

1) java 6 改進(jìn)了 SQLException 類,讓其實(shí)現(xiàn)了 Iterable接口, 其 iterator() 方法可以產(chǎn)生一個(gè) Iterable< Throwable>;

  • 1.1) 這個(gè)迭代器是可以迭代這兩個(gè)鏈, 首先迭代第一個(gè) SQLException 的成因鏈, 然后迭代下一個(gè) SQLException ,以此類推;如,

    for(Throwable t : sqlException)
    {
    do sth with t
    }

  • 1.2)可以在 SQLException 上調(diào)用 getSQLState 和 getErrorCode 方法來(lái)進(jìn)一步分析它;

2) SQLException 按照層次結(jié)構(gòu)樹(shù)的方式組合到了一起, 如下圖所示:

  • 2.1)數(shù)據(jù)庫(kù)驅(qū)動(dòng)程序?qū)⒎侵旅鼏?wèn)題作為警告報(bào)告,我們可以從連接(Connection), 語(yǔ)句(Statement)或結(jié)果集(ResultSet)中獲取這些警告;
  • 2.2)SQLWarning: 是 SQLException的子類,我們可以調(diào)用 getSQLState 和 getErrorCode 來(lái)獲取有關(guān)警告的更多信息; (干貨——SQLWarning 定義)
  • 2.3)要獲得所有警告,使用下面的循環(huán):

    SQLWarning w = stat.getWarning()
    while(w != null)
    {
    do wth with w
    w = w.nextWarning();
    }

  • 2.4)當(dāng)數(shù)據(jù)從數(shù)據(jù)庫(kù)中讀出并意外被截?cái)鄷r(shí), SQLWarning 的 DataTruncation 子類就派上用場(chǎng)了; 如果數(shù)據(jù)截?cái)喟l(fā)送在更新語(yǔ)句中, 那么DataTrucation 將會(huì)被當(dāng)做異常拋出;


【4】組裝數(shù)據(jù)庫(kù)

1)看個(gè)荔枝:(用java 操作數(shù)據(jù)庫(kù))

  • step1)連接數(shù)據(jù)庫(kù)。

    • step1.1) getConnection 方法:讀取database.properties 文件中的 屬性信息,并將屬性jdbc.drivers 添加到系統(tǒng)屬性中;
    • step1.2) 驅(qū)動(dòng)程序管理器:使用屬性jdbc.drivers 加載相應(yīng)的驅(qū)動(dòng)程序;
    • step1.3) getConnection方法: 使用 jdbc.url , jdbc.username, jdbc.password 等屬性打開(kāi)數(shù)據(jù)庫(kù)連接;
  • step2)使用 sql 語(yǔ)句打開(kāi)文件;

  • step3) 使用 泛化的execute 方法執(zhí)行每條語(yǔ)句;
  • step4) 如果產(chǎn)生了結(jié)果集, 則打印結(jié)果;
  • step5) 如果運(yùn)行過(guò)程中出現(xiàn) SQL 異常, 則打印出這個(gè)異常以及所有可能包含在其中的與其連接在一起的相關(guān)異常;
  • step6)關(guān)閉數(shù)據(jù)庫(kù)連接;

2)運(yùn)行結(jié)果如下:

(java -classpath .;D:\Software_Cluster\Development\mysql\mysql-connector-java-5.1.17\mysql-connector-java-5.1.17-bin.jar com.corejava.chapter4.ExecSQL)

3)source code at a glance

class ExecSQL {private static String cur_dir = System.getProperty("user.dir") + File.separator + "com" + File.separator + "corejava" + File.separator + "chapter4" + File.separator;public static void main(String args[]) throws IOException{try{Scanner in = args.length == 0 ? new Scanner(System.in) : new Scanner(Paths.get(args[0]));try (Connection conn = getConnection()){Statement stat = conn.createStatement();while (true){if (args.length == 0) System.out.println("Enter command or EXIT to exit:");if (!in.hasNextLine()) return;String line = in.nextLine();if (line.equalsIgnoreCase("EXIT")) return;if (line.trim().endsWith(";")) // remove trailing semicolon{line = line.trim();line = line.substring(0, line.length() - 1);}try{boolean isResult = stat.execute(line);if (isResult){ResultSet rs = stat.getResultSet(); //結(jié)果集showResultSet(rs); // 打印結(jié)果集}else{int updateCount = stat.getUpdateCount();System.out.println(updateCount + " rows updated");}}catch (SQLException ex){for (Throwable e : ex)e.printStackTrace();}}}}catch (SQLException e){for (Throwable t : e)t.printStackTrace();}}public static Connection getConnection() throws SQLException, IOException{Properties props = new Properties();try (InputStream in = Files.newInputStream(Paths.get(cur_dir + "database.properties"))){props.load(in);}String drivers = props.getProperty("jdbc.drivers");if (drivers != null) System.setProperty("jdbc.drivers", drivers);String url = props.getProperty("jdbc.url");String username = props.getProperty("jdbc.username");String password = props.getProperty("jdbc.password");return DriverManager.getConnection(url, username, password);}public static void showResultSet(ResultSet result) throws SQLException{ResultSetMetaData metaData = result.getMetaData(); // 結(jié)果集元數(shù)據(jù)int columnCount = metaData.getColumnCount();for (int i = 1; i <= columnCount; i++){if (i > 1) System.out.print(", ");System.out.print(metaData.getColumnLabel(i));}System.out.println();while (result.next()) // 循環(huán)打印結(jié)果集{for (int i = 1; i <= columnCount; i++){if (i > 1) System.out.print(", ");System.out.print(result.getString(i));}System.out.println();}} }

總結(jié)

以上是生活随笔為你收集整理的java数据库编程——执行SQL 语句的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。