2010-04-16 34 views
12

Tôi thề rằng điều này được sử dụng để làm việc, nhưng nó không phải trong trường hợp này. Tôi đang cố gắng để phù hợp với col1, col2 và col3, ngay cả khi một hoặc nhiều người trong số họ là null. Tôi biết rằng trong một số ngôn ngữ tôi đã phải nghỉ mát để circumlocutions như ((? is null AND col1 is null) OR col1 = ?). Điều đó có cần thiết ở đây không?Ràng buộc một biến rỗng trong một PreparedStatement

 PreparedStatement selStmt = getConn().prepareStatement(
       "SELECT  * " + 
       "FROM  tbl1 " + 
       "WHERE  col1 = ? AND col2 = ? and col3 = ?"); 
     try 
     { 
      int col = 1; 
      setInt(selStmt, col++, col1); 
      setInt(selStmt, col++, col2); 
      setInt(selStmt, col++, col3); 
      ResultSet rs = selStmt.executeQuery(); 
      try 
      { 
       while (rs.next()) 
       { 
        // process row 
       } 
      } 
      finally 
      { 
       rs.close(); 
      } 
     } 
     finally 
     { 
      selStmt.close(); 
     } 

    // Does the equivalient of stmt.setInt(col, i) but preserves nullness. 
    protected static void setInt(PreparedStatement stmt, int col, Integer i) 
    throws SQLException 
    { 
     if (i == null) 
      stmt.setNull(col, java.sql.Types.INTEGER); 
     else 
      stmt.setInt(col, i); 
    } 
+0

Xem thêm http://en.wikipedia.org/wiki/Null_%28SQL%29#Three-valued_logic_.283VL.29 – trashgod

Trả lời

9

Điều này có thể phụ thuộc vào trình điều khiển JDBC, nhưng đối với hầu hết các phần, có, bạn sẽ cần phải sử dụng biểu mẫu mở rộng hơn bạn hiển thị ở trên.

Các câu lệnh chuẩn bị JDBC thường là các trình bao bọc tương đối mỏng xung quanh việc triển khai thực hiện truy vấn được tham số hóa gốc, tức là truy vấn với? thay cho các tham số được chuyển tới trình biên dịch truy vấn và được biên dịch, vì vậy, sau này, khi bạn gọi stmt.executeQuery(), câu lệnh không thể được điều chỉnh từ một số column = ? thành column IS NULL. Đây không phải là quá nhiều hạn chế của JDBC vì nó là the semantics of NULL in SQL. Đối với SQL x = NULL không được xác định là x <> NULL.

Điều đó nói rằng, một số tài xế JDBC có thể vi phạm các khái niệm về NULL -ity trong SQL và cho phép setNull() để chuyển đổi báo cáo kết quả = ?-IS NULL này sẽ là hành vi rất phi tiêu chuẩn (mặc dù nó có thể dễ dàng thực hiện bằng cách viết một số phương thức xử lý trước truy vấn).

1

Nói chung cái gì đó là bằng NULL luôn là sai (thậm chí NULL, vì vậy SELECT * FROM tbl WHERE NULL=NULL; sẽ là một tập rỗng), vì vậy có thể bạn cần phải làm điều đó một chặng đường dài nếu bạn muốn chấp nhận sự bình đẳng rỗng như

rằng
+0

@ michael-Mrozek 'Ở ĐÂU NULL = NULL' thực sự trả về 'NULL'. Vì vậy, ví dụ, 'SELECT * FROM tbl WHERE NOT (NULL = NULL)' cũng dẫn đến một tập rỗng. – ig0774

3

Bạn đang sử dụng cơ sở dữ liệu nào?

Nhưng ít nhất với Oracle, bình đẳng (và bất bình đẳng) không bao giờ khớp với NULL, bạn phải viết IS NOT NULL.

0

Tôi biết đó là quá muộn có lẽ, nhưng chỉ vì lợi ích của nó một hack cho Oracle mà dường như tôi làm việc:

SQL:

SELECT.....FROM....WHERE NVL(CUST_ID,0)=? AND NVL(vendor_id,0)=? 

Và trong mã nơi bạn làm một cái gì đó gọi jdbc như thế này:

pstmt.setString(1, (xxo.getCustId().equals("")) ? "0":xxo.getCustId()); 
pstmt.setString(2, (xxo.getVendId().equals("")) ? "0":xxo.getVendId()); 
rs = pstmt.executeQuery(); 
+0

Chỉ hoạt động nếu bạn hoàn toàn tích cực biết rằng "0" không phải là một chuỗi hợp lệ trong cột. –

+0

Có, tôi đồng ý. Tôi sử dụng nó trong các cột mà tôi mong đợi dữ liệu và 0 không phải là một trong số đó và chắc chắn null cũng không phải là một lựa chọn. Đó là một mẹo hay Tôi nghĩ .... – hephestos

+0

Tại sao không "CUST_ID =? OR (? IS NULL và CUST_ID IS NULL)"? – MikeB

Các vấn đề liên quan