2017-04-25 32 views
2

我是Java新手,我的工作都與JDBC相關 - 關於插入和處理數據。在其所有工作正常。單嘗試捕獲塊中的多個JDBC語句。這是好的做法嗎?

要減少代碼使用單個try{} catch()塊來編寫多個JDBCStatementsPrepared Statements

示例代碼:

public void dashboardReports() 
{ 
    try { 

     String total_stock_value="select sum(price*closingstock)as tsv from purchase_table"; 
     Statement ps_tsv=connection.createStatement(); 
     ResultSet set_tsv=ps_tsv.executeQuery(total_stock_value); 
     if(set_tsv.next()) 
     { 
      total_stock.setText(set_tsv.getString("tsv"));    
     }   

     String tota_sales="select sum(INVOICE_VALUE) as iv from PARTYWISE_ACCOUNTS_LEDGER"; 
     Statement st_total_sales=connection.createStatement(); 
     ResultSet set_total_sales=st_total_sales.executeQuery(tota_sales); 
     if(set_total_sales.next()) 
     { 
      total_sales.setText(set_total_sales.getString("iv")); 
     }   

     String total_purchases="select sum(CP_INVOICEVALUE)as cpi from COMPANY_PAYMENTS"; 
     Statement st_tps=connection.createStatement(); 
     ResultSet set_tps=st_tps.executeQuery(total_purchases); 
     if(set_tps.next()) 
     { 
      total_purchases_label.setText(set_tps.getString("cpi")); 
     } 

     String total_collectionss="select sum(PAYMENT_REC) as payrec from PARTYWISE_ACCOUNTS_LEDGER"; 
     Statement ps_toco=connection.createStatement(); 
     ResultSet set_toco=ps_toco.executeQuery(total_collectionss); 
     if(set_toco.next()) 
     { 
      total_collections.setText(set_toco.getString("payrec")); 
     } 

     String total_payments="select sum(CP_PAYMENTREC) as paid from COMPANY_PAYMENTS"; 
     Statement ps_topa=connection.createStatement(); 
     ResultSet set_topa=ps_topa.executeQuery(total_payments); 
     if(set_topa.next()) 
     { 
      total_payments_label.setText(set_topa.getString("paid")); 
     } 

    } catch (Exception e) { 
     // TODO: handle except 
    } 
} 

因此,這是很好的應對或其他別的辦法?

截至目前我的代碼工作得很好,我們是否有任何未來的問題與這種方法。

+1

如果這個代碼工作正常,你應該提交我們的[代碼審查(HTTPS:/ /codereview.stackexchange.com/)姊妹網站。 –

+0

我看到的最大的問題是,如果您不使用試用資源來解決問題,並且您會自動使用較小範圍的嘗試塊,則不會關閉資源。順便說一下:你的代碼效率低下:當你查詢這兩個表時,你只查詢兩次表,只能查詢一次。 –

回答

2

由於您只是在這裏執行SELECT操作,因此不需要顯式事務,因爲您沒有更改數據庫的狀態,也沒有任何可以回滾的地方。將單個try塊中的所有SELECT語句分組沒有任何問題。但是,有一個潛在的缺點,即如果一個SELECT失敗,您的代碼將退出該try塊,所有後續查詢將不會運行。如果你可以容忍這一點,那麼你可以保持原樣。與此類似的是一系列串聯連接的燈泡;如果一個人休息,他們都會出去。

對於每個查詢,您可以使用單獨的try塊。然後,即使其中一個發生異常,其他人也可能成功完成。這裏的比喻將是一系列並聯電路中的燈泡。

0

只要確保你閉上你的語句和結果集:

try { 

    String total_stock_value="select sum(price*closingstock)as tsv from purchase_table"; 
    try (Statement ps_tsv=connection.createStatement(); 
     ResultSet set_tsv=ps_tsv.executeQuery(total_stock_value)) { 
     if(set_tsv.next()) 
     { 
      total_stock.setText(set_tsv.getString("tsv")); 
     } 
    } 

    String tota_sales="select sum(INVOICE_VALUE) as iv from PARTYWISE_ACCOUNTS_LEDGER"; 
    try (Statement st_total_sales=connection.createStatement(); 
      ResultSet set_total_sales=st_total_sales.executeQuery(tota_sales)) { 
     if(set_total_sales.next()) 
     { 
      total_sales.setText(set_total_sales.getString("iv")); 
     } 
    } 

    String total_purchases="select sum(CP_INVOICEVALUE)as cpi from COMPANY_PAYMENTS"; 
    try (Statement st_tps=connection.createStatement(); 
      ResultSet set_tps=st_tps.executeQuery(total_purchases)) { 
     if(set_tps.next()) 
     { 
      total_purchases_label.setText(set_tps.getString("cpi")); 
     } 
    } 

    String total_collectionss="select sum(PAYMENT_REC) as payrec from PARTYWISE_ACCOUNTS_LEDGER"; 
    try (Statement ps_toco=connection.createStatement(); 
      ResultSet set_toco=ps_toco.executeQuery(total_collectionss)) { 
     if(set_toco.next()) 
     { 
      total_collections.setText(set_toco.getString("payrec")); 
     } 
    } 

    String total_payments="select sum(CP_PAYMENTREC) as paid from COMPANY_PAYMENTS"; 
    try (Statement ps_topa=connection.createStatement(); 
      ResultSet set_topa=ps_topa.executeQuery(total_payments)) { 
     if(set_topa.next()) 
     { 
      total_payments_label.setText(set_topa.getString("paid")); 
     } 
    } 

} catch (Exception e) { 
    // TODO: handle except 
} 

}

1

如果你很高興與所有後續SELECT■如果一個失敗,失敗,那麼我會改變拋出一個異常的方法

public void dashboardReports() throws SQLException 
{ 
.... 
} 

然後從調用方法中捕獲SQLException。

注意我覺得這是更好地拋出/搭上SQLException而非Exception

+0

有點類似於我剛剛寫的...反饋是歡迎那裏。 – GhostCat

2

我覺得你的代碼就可以了。 您最後需要在塊中關閉結果集,語句和連接。

0

更好的方法是創建一個方法,做常用的操作:當調用此方法與try catch塊圍繞着它

public String execute(String query) throws SQLException { 
Statement ps_toco=connection.createStatement(); 
     ResultSet set_toco=ps_toco.executeQuery(query); 
     return set_toco.next(); 
} 

0

1.您可以使用像executeQuery(Connection conn, Statement st, String sql)這樣的方法來封裝和縮減您的代碼行。

2.不要依賴於通用Exception,捕獲SQL特定的異常類太

3。我沒有在那裏看到finally塊,以便正確關閉資源,除非您在其他地方執行此操作。或者,你可以嘗試使用try with resource語法消除需要finally

4.See的,你需要在catch塊做什麼 - 你需要異常傳播鏈向上上方或失敗的計劃在那裏?

5.In我看來,一個ResultSetStatement需要活得短,因爲他們可以因此嘗試,只要你能關閉它們 - 不要等到全部關閉單塊。點#1將有助於實現這一點。

從技術的正確性和有效性的角度來看,在編寫代碼方面沒有任何壞處 - 對所有SQL使用單個try-catch並且排除任何異常(因爲我看到的只有SELECT sqls),但是有乾淨,可讀和可維護的代碼,在這方面,你的代碼看起來很差。

2

這違反了Single ResponsbilitySingle Layer of Abstraction原則。

所以,儘管這段代碼在技術上是有效的,您不僅應該關注其正確性,還應該關注其可讀性。和可測性。而且我認爲你所展示的輸入內容都不是「很棒」。

因此;來自乾淨的代碼(質量)角度;我寧願建議去沿着線的東西:

outer method ... 
    try { 
    helperMethod1(); 
    helperMethod2(); 
    } catch(... 

的小幫手你們每個人到了那裏不同的情況。當然,你不會停留在那裏;但嘗試隔離共同方面的幫手;並可能找到方法與單一的,更通用的幫手。

當然:你儘量避免捕獲例外如果可能的話。相反,你可以捕獲最具體的例外!

+2

+1我同意你的意見,甚至想補充一點,因爲'helperMethod1'和'helperMethod2'在功能上幾乎完全相同,所以它們可能被重構爲一個參數化方法 –

+0

好主意。把我的答案說成是這個。 – GhostCat

0

儘管您的代碼有效,但我強烈建議您將重構爲更好的維護和可讀性,如下所示。此外,確保資源被正確關閉:

public void dashboardReports() { 
    handleTotalStocks(); 
    handleTotalSales(); 
    handleTotalPurchages(); 
    //Add others 
} 

handleTotalStocks()方法:

private void handleTotalStocks() { 
     String total_stock_value="select sum(price*closingstock)as tsv 
        from purchase_table"; 

    try(Statement ps_tsv=connection.createStatement(); 
     ResultSet set_tsv=ps_tsv.executeQuery(total_stock_value);) { 
     if(set_tsv.next()) { 
      total_stock.setText(set_tsv.getString("tsv")); 
     } 
     } 
    } 
//add other methods 
相關問題