JDBC 基礎(chǔ)(3)
發(fā)表時(shí)間:2024-05-19 來(lái)源:明輝站整理相關(guān)軟件相關(guān)文章人氣:
[摘要]創(chuàng)建表 首先,我們?cè)谖覀兊氖纠龜?shù)據(jù)庫(kù)創(chuàng)建其中一張表 COFFEES,包含在咖啡店所賣(mài)咖啡的必要的信息,包括咖啡名字,他們的價(jià)格,本星期賣(mài)了多少磅及迄今為止賣(mài)的數(shù)目。關(guān)于 COFFEES 表我們以后會(huì)詳細(xì)描述,如下: COF_NAME SUP_ID PRICE SALES TOTAL Colom...
創(chuàng)建表
首先,我們?cè)谖覀兊氖纠龜?shù)據(jù)庫(kù)創(chuàng)建其中一張表 COFFEES,包含在咖啡店所賣(mài)咖啡的必要的信息,包括咖啡名字,他們的價(jià)格,本星期賣(mài)了多少磅及迄今為止賣(mài)的數(shù)目。關(guān)于 COFFEES 表我們以后會(huì)詳細(xì)描述,如下:
COF_NAME SUP_ID PRICE SALES TOTAL
Colombian 101 7.99 0 0
French_Roast 49 8.99 0 0
Espresso 150 9.99 0 0
Colombian_Decaf 101 8.99 0 0
French_Roast_Decaf 49 9.99 0 0
存儲(chǔ)咖啡名的列是 COF_NAME,它的 SQL 數(shù)據(jù)類型是 VARCHAR,最大的長(zhǎng)度為 32 個(gè)字符。因?yàn)槲覀兯u(mài)的每種類型咖啡都使用不同的名字,名字可用于作為唯一識(shí)別咖啡的標(biāo)識(shí),因此可用于作主鍵。第二個(gè)列叫 SUP_ID,用于保存咖啡供應(yīng)商標(biāo)識(shí);其 SQL 數(shù)據(jù)類型為 INTEGER。第 3 列叫 PRICE,因?yàn)樗枰4鎺?shù)的十進(jìn)制數(shù),因此它的 SQL 類型為 FLOAT。(注意,通常錢(qián)的 SQL 類型為 DECIMAL 或 NUMERIC,但在不同 DBMSs 間存在差異,為了避免于老版本的 JDBC 的不兼容性在本教程我們采用更標(biāo)準(zhǔn)的 FLOAT 類型)SALES 列的 SQL 類型為 INTEGER,其值為本星期所賣(mài)咖啡的磅數(shù)。最后一列,TOTAL 的 SQL 類型為 INTEGER,保存了迄今為止所賣(mài)咖啡的總磅數(shù)。
數(shù)據(jù)庫(kù)里的第二個(gè)表 SUPPLIERS,保存了每個(gè)供應(yīng)商的信息:
SUP_ID SUP_NAME STREET CITY STATE ZIP
101 Acme, Inc. 99 Market Street Groundsville CA 95199
49 Superior Coffee 1 Party Place Mendocino CA 95460
150 The High Ground 100 Coffee Lane Meadows CA 93966
COFFEES 跟 SUPPLIERS 都包含列 SUP_ID,它意味著可以用 SELECT 語(yǔ)句從這兩張表中取得有關(guān)信息。列 SUP_ID 是 SUPPLIERS 表的主鍵,用于唯一識(shí)別每個(gè)咖啡供應(yīng)商。在 COFFEES 表中,SUP_ID 列被稱外鍵。注意每個(gè) SUP_ID 值在 SUPPLIERS 表里只出現(xiàn)一次;這對(duì)主鍵是必須的。在 COFFEES 表里,它作為外鍵,顯然它可以有重復(fù)的 SUP_ID 值,因?yàn)橥还⿷?yīng)商可以提供很多種的咖啡。在本節(jié)的最后,你將看見(jiàn)如何在 SELECT 語(yǔ)句中使用主鍵及外鍵的一個(gè)例子。
下面的 SQL 語(yǔ)句用于創(chuàng)建 COFFEES 表。列由列名跟空格跟 SQL 類型組成。列(包括列名及其 SQL 類型)跟下一個(gè)之間用逗號(hào)分隔。VARCHAR 類型創(chuàng)建定義了最大長(zhǎng)度, 因此它需要有一個(gè)參數(shù)來(lái)表示最大長(zhǎng)度。參數(shù)必須在類型后面的括號(hào)內(nèi)。SQL 語(yǔ)句如下,列 COF_NAME 的長(zhǎng)度 被限定為不得超過(guò) 32 個(gè)字符:
CREATE TABLE COFFEES
(COF_NAME VARCHAR(32),
SUP_ID INTEGER,
PRICE FLOAT,
SALES INTEGER,
TOTAL INTEGER)
這些代碼不帶 DBMS 語(yǔ)句結(jié)束符, 因?yàn)槊總(gè) DBMS 都可能不同。例如, Oracle 使用一個(gè)分號(hào) (;) 作為語(yǔ)句的結(jié)束,而 Sybase 使用 go。你所使用的驅(qū)動(dòng)程序會(huì)自動(dòng)提供合適的語(yǔ)句結(jié)束符,因此你無(wú)須把它包括在你的 JDBC 代碼中。
另外,我們應(yīng)該指出的的是 SQL 語(yǔ)句的格式。在 CREATE TABLE 語(yǔ)句中,關(guān)鍵字采用大寫(xiě)字符,并且每個(gè)項(xiàng)目都另起一行。SQL 并沒(méi)有此要求;僅僅是為了更容易閱讀。SQL 標(biāo)準(zhǔn)是不區(qū)分關(guān)鍵詞的大小寫(xiě)的, 因此,如下例中的 SELECT 語(yǔ)句可以有多種寫(xiě)法。因此下面兩個(gè)不同寫(xiě)法的語(yǔ)句對(duì) SQL 來(lái)說(shuō)是一樣的。
SELECT First_Name, Last_Name
FROM Employees
WHERE Last_Name LIKE "Washington"
select First_Name, Last_Name from Employees where
Last_Name like "Washington"
然而,引號(hào)里的內(nèi)容是區(qū)分大小寫(xiě)的:在名字"Washington" 里 "W" 必須被大寫(xiě),并且余下的字符必須是小寫(xiě)的。
對(duì)于標(biāo)識(shí),不同的 DBMS 有不同的要求,例如, 某些 DBMSs 要求那些列名及表名必須跟創(chuàng)建時(shí)的一樣,有些則沒(méi)有此要求。為安全起見(jiàn),我們?nèi)渴褂么髮?xiě)標(biāo)識(shí)如 COFFEES、SUPPLIERS,因?yàn)槲覀兪悄菢佣x他們的。
到止我們寫(xiě)了創(chuàng)建 COFFEES 表的 SQL 語(yǔ)句,F(xiàn)在我們?cè)谒饷婕由弦?hào)(使它成為字符串),并且字符串賦值給變量 createTableCoffees,在以后的 JDBC 代碼中我們可以使用此變量。正如看到的,DBMS 并不在意分行,但對(duì) Java 語(yǔ)言來(lái),String 對(duì)象分行是通不過(guò)編譯的。因而,我們可以用加號(hào) (+) 把每一行的串連接。
String createTableCoffees = "CREATE TABLE COFFEES " +
"(COF_NAME VARCHAR(32), SUP_ID INTEGER, PRICE FLOAT, " +
"SALES INTEGER, TOTAL INTEGER)";
我們?cè)?CREATE TABLE 語(yǔ)句中使用的數(shù)據(jù)類型是通用的 SQL 類型(也稱 JDBC 類型)它們?cè)陬?java.sql.Types 中定義。DBMSs 通常使用這些標(biāo)準(zhǔn)的類型,因此,當(dāng)你要嘗試一些 JDBC 應(yīng)用程序時(shí),你可以直接使用 CreateCoffees.java 應(yīng)用程序,它使用了 CREATE TABLE 語(yǔ)句。如果你的 DBMS 使用了它的自己的本地的類型名字,我們?yōu)槟愎⿷?yīng)其它的應(yīng)用程序,我們將在后面詳細(xì)解釋。
在運(yùn)用任何應(yīng)用程序前,當(dāng)然,我們將讓你了解 JDBC 的基礎(chǔ)。
創(chuàng)建 JDBC Statements 對(duì)象
Statement 對(duì)象用于把 SQL 語(yǔ)句發(fā)送到 DBMS 。你只須簡(jiǎn)單地創(chuàng)建一個(gè) Statement 對(duì)象并且然后執(zhí)行它,使用適當(dāng)?shù)姆椒▓?zhí)行你發(fā)送的 SQL 語(yǔ)句。對(duì) SELECT 語(yǔ)句來(lái)說(shuō),可以使用 executeQuery。要?jiǎng)?chuàng)建或修改表的語(yǔ)句,使用的方法是 executeUpdate。
需要一個(gè)活躍的連接的來(lái)創(chuàng)建 Statement 對(duì)象的實(shí)例。在下面的例子中,我們使用我們的 Connection 對(duì)象 con 創(chuàng)建 Statement 對(duì)象 stmt:
Statement stmt = con.createStatement();
到此 stmt 已經(jīng)存在了,但它還沒(méi)有把 SQL 語(yǔ)句傳遞到 DBMS。我們需要提供 SQL 語(yǔ)句作為參數(shù)提供給我們使用的 Statement 的方法。例如,在下面的代碼段里,我們使用上面例子中的 SQL 語(yǔ)句作為 executeUpdate 的參數(shù):
stmt.executeUpdate("CREATE TABLE COFFEES " +
"(COF_NAME VARCHAR(32), SUP_ID INTEGER, PRICE FLOAT, " +
"SALES INTEGER, TOTAL INTEGER)");
因?yàn)槲覀円呀?jīng)把 SQL 語(yǔ)句賦給了 createTableCoffees 變量,我們可以如下方式書(shū)寫(xiě)代碼:
stmt.executeUpdate(createTableCoffees);
執(zhí)行語(yǔ)句
我們使用 executeUpdate 方法是因?yàn)樵?createTableCoffees 中的 SQL 語(yǔ)句是 DDL (數(shù)據(jù)定義語(yǔ)言)語(yǔ)句。創(chuàng)建表,改變表,刪除表都是 DDL 語(yǔ)句的例子,要用 executeUpdate 方法來(lái)執(zhí)行。你也可以從它的名字里看出,方法 executeUpdate 也被用于執(zhí)行更新表 SQL 語(yǔ)句。實(shí)際上,相對(duì)于創(chuàng)建表來(lái)說(shuō),executeUpdate 用于更新表的時(shí)間更多,因?yàn)楸碇恍枰獎(jiǎng)?chuàng)建一次,但經(jīng)常被更新。
被使用最多的執(zhí)行 SQL 語(yǔ)句的方法是 executeQuery。這個(gè)方法被用來(lái)執(zhí)行 SELECT 語(yǔ)句,它幾乎是使用最多的 SQL 語(yǔ)句。馬上你將看到如何使用這個(gè)方法。
在表中輸入數(shù)據(jù)
我們已經(jīng)顯示了如何通過(guò)指定列名、數(shù)據(jù)類型來(lái)創(chuàng)建表 COFFEES,但是這僅僅建立表的結(jié)構(gòu)。表還沒(méi)有任何數(shù)據(jù)。我們將次輸入一行數(shù)據(jù)到表中,提供每列的信息,注意插入的數(shù)據(jù)顯示順序跟表創(chuàng)建時(shí)候是一樣的,既缺省順序。
下列代碼插入一個(gè)行數(shù)據(jù),COF_NAME 的值為 Colombian,SUP_ID 為 101,PRICE 為 7.99,SALES 0,TOTAL 0。就象創(chuàng)建 COFFEES 表一樣,我們創(chuàng)建一 Statement 對(duì)象,并執(zhí)行 executeUpdate 方法。
因?yàn)?SQL 語(yǔ)句一行顯示不下,因此我們把它分為兩行,并用加號(hào) (+) 相連。特別要注意的是,在 COFFEES 和 VALUES 之間要有空格。這個(gè)空格必須在引號(hào)之內(nèi)并且要在 COFFEES 跟 VALUES 之間;沒(méi)有這個(gè)空格,SQL 語(yǔ)句將被錯(cuò)誤地被讀作為 "INSERT INTO COFFEESVALUES ...",并且 DBMS 將尋找表 COFFEESVALUES。還要注意的是在 coffee name 上我們使用了單引號(hào)。
Statement stmt = con.createStatement();
stmt.executeUpdate(
"INSERT INTO COFFEES " +
"VALUES (`Colombian`, 101, 7.99, 0, 0)");
下面的代碼把第二行插入到表 COFFEES 中。我們可以在使用 Statement 對(duì)象而無(wú)須為每次執(zhí)行創(chuàng)建一個(gè)新的。
stmt.executeUpdate("INSERT INTO COFFEES " +
"VALUES (`French_Roast`, 49, 8.99, 0, 0)");
剩下行的數(shù)據(jù)如下:
stmt.executeUpdate("INSERT INTO COFFEES " +
"VALUES (`Espresso`, 150, 9.99, 0, 0)");
stmt.executeUpdate("INSERT INTO COFFEES " +
"VALUES (`Colombian_Decaf`, 101, 8.99, 0, 0)");
stmt.executeUpdate("INSERT INTO COFFEES " +
"VALUES (`French_Roast_Decaf`, 49, 9.99, 0, 0)");
從表中取得數(shù)據(jù)
既然表 COFFEES 中已經(jīng)有數(shù)據(jù)了,我們就可以寫(xiě)一個(gè) SELECT 語(yǔ)句來(lái)取得這些值。下面的 SQL 語(yǔ)句中星號(hào) (*) 表示選擇所有的列。因?yàn)闆](méi)有用 WHERE 子句來(lái)限制所選的行,因此下面的 SQL 語(yǔ)句選擇的是整個(gè)表。
SELECT * FROM COFFEES
結(jié)果是整個(gè)表的數(shù)據(jù),如下:
COF_NAME SUP_ID PRICE SALES TOTAL
--------------- ------ ----- ----- -----
Colombian 101 7.99 0 0
French_Roast 49 8.99 0 0
Espresso 150 9.99 0 0
Colombian_Decaf 101 8.99 0 0
French_Roast_Decaf 49 9.99 0 0
如果你直接在數(shù)據(jù)庫(kù)系統(tǒng)里輸入 SQL 查詢語(yǔ)句,你將在你的終端上看到如上的結(jié)果。當(dāng)我們通過(guò)一個(gè) Java 應(yīng)用程序存取一個(gè)數(shù)據(jù)庫(kù)時(shí),正如我們馬上要做的一樣,我們需要檢索結(jié)果以便我們能使用他們。你將在下一節(jié)看到如何實(shí)現(xiàn)。
這是 SELECT 語(yǔ)句的另一個(gè)例子,這將得到咖啡及其各自每磅單價(jià)的列表。
SELECT COF_NAME, PRICE FROM COFFEES
查詢的結(jié)果集將具有如下形式:
COF_NAME PRICE
-------- ---------- -----
Colombian 7.99
French_Roast 8.99
Espresso 9.99
Colombian_Decaf 8.99
French_Roast_Decaf 9.99
上面 SELECT 語(yǔ)句取得了所有咖啡的名字及價(jià)格。而下面的 SELECT 語(yǔ)句限制那些每磅價(jià)格低于 $9.00 的咖啡才被選擇。
SELECT COF_NAME, PRICE
FROM COFFEES
WHERE PRICE < 9.00
結(jié)果集將具有如下形式:
COF_NAME PRICE
-------- ------- -----
Colombian 7.99
French_Roast 8.99
Colombian Decaf 8.99