2012-04-02 46 views
6

根據java.sql.StatementdocumentationgetResultSet,它說:的getResultSet()「應該被稱爲每個結果只有一次」

檢索當前結果作爲ResultSet對象。每個結果只能調用一次該方法 。

使用一些測試代碼,我跑executeQuery()並多次打電話給getResultSet()並觀察返回的ResultSet指向同一個對象。所以我猜測它不會返回一個不同的ResultSet,你需要單獨關閉它。但是,這當然可以是我的JDBC驅動程序獨有的。

縱觀documentationResultSet它說:

默認的ResultSet對象不可更新,並具有遊標 向前移動而已。因此,只能從第一行到最後一行遍歷一次,並且只能遍歷一次。

這似乎是一個很好的理由,因爲它可能導致一些「陷阱」的情況多次調用它可能不是一個好主意。如果這是唯一的原因,我覺得他們可能只是說,所以我認爲可能比這更多。

因此,有誰知道爲什麼每個結果不應該多次調用getResultSet?這question是讓我好奇的第一個地方。

+1

沒有發佈這個答案,因爲它只是一個預感,但我懷疑這是給JDBC驅動程序開發人員留有餘地的方法,使他們無法定義當你多次調用它時會發生什麼。在你的特定情況下,它可以工作,但如果你曾經切換JDBC驅動程序,它可能不會。 – 2012-04-02 22:19:06

+1

我認爲它就像這樣簡單:ResultSet對象具有狀態。只有一個ResultSet對象作爲Statement的成員。獲取對象不會重新執行語句。如果您在第一次獲得後修改了某些內容,則無法保證第二次獲取對象與第一次獲取對象的狀態相同。所以這只是一個謹慎。查看Postres jdbc驅動程序(org.postgresql.jdbc2.AbstractJdbc2Statement),我們可以看到它在內部使得許多調用像這樣:return(result!= null && result.getResultSet()!= null); – Glenn 2012-04-03 01:08:13

回答

4

ResultSet對象是由Java JDBC提供的接口 - 它們不提供實現。即使您的特定數據庫代碼和相關驅動程序實施了ResultSet,因此您可以在每個結果上多次調用它,如果您依賴於合同外的這種行爲,那麼您當然在玩火。

與合同編寫this method should be called only once per result系列的一個可能原因是出於效率原因。構建ResultSet很可能會對數據庫進行JDBC RPC調用,並且JDBC規範的作者希望阻止多次往返。他們可能不希望強制執行者有效地防止每個結果多次調用。再說一次,即使你的數據庫正在防範這種行爲,但並不意味着下一次會有這種行爲。

大多數ResultSet實現也保持與數據庫打開的連接,以便當您獲得某些字段(如大塊)時,它可以回調數據庫以獲取數據。使用多個對象的相同連接打開或(更糟糕)多個連接將非常危險/令人困惑。

此外,他們可能一直擔心代碼的兩部分調用getResultSet()兩次,並返回對同一個單一非同步對象的引用。這會在調用next()時引起混淆,並用多個引用覆蓋該對象。

我在猜測當然,但我希望這有助於。

+0

絕對有幫助!如果我沒有記錯,關閉「ResultSet」不會關閉任何可能創建的斑點。關於多連接的第三段我有點困惑。 ResultSet'不會使用相同的'Connection'從數據庫中檢索任何數據嗎?另外,我不清楚爲什麼來自多個ResultSet的'Connection'是不好的 - 我敢肯定,我忽略了一些明顯的東西。另外,如果你可以提供一個例子(即使它是針對特定的JDBC驅動程序的)調用getResult兩次的問題,我認爲這將是一個完美的答案。 – nevets1219 2012-04-03 21:41:31

+0

重新第三段,我只是說連接管理是一個問題。如果有多個Connection對象的副本,或者如果兩個線程都有一個ResultSet並且正在對同一個非同步的Connection執行操作,那就很危險。 – Gray 2012-04-03 21:46:08

+0

舉例來說,我沒有時間。這是關於違反合同的。 Postgres可能會升級他們的驅動程序並稍微改變行爲,但仍然履行合同,並且如果您要依靠多個調用工作,代碼將會中斷。這是一個原則問題。 – Gray 2012-04-03 21:47:29

相關問題