准备语句IN子句Java Microsoft JDBC

时间:2015-12-15 21:39:55

标签: jdbc prepared-statement

我在这里和其他地方看过这样的例子,说这应该有用 在IN CLAUSE中使用'1'参数我获得了成功:

SELECT AVG( ( High_Temperature + Low_Temperature ) / 2.0 ) 
  FROM obs_masterAll 
  WHERE Observation_Valid_Time = ? AND 
        Location_ID IN ( ? );

Microsoft JDBC Driver 4.2 for SQL Server  4.2.6420.100
Parameter Count = 2
2010, 36.5

但是,如果在IN CLAUSE中有多个参数,我会得到:

SELECT AVG( ( High_Temperature + Low_Temperature ) / 2.0 ) 
  FROM obs_masterAll 
  WHERE Observation_Valid_Time = ? 
  AND Location_ID IN ( ?, ? );      <--- PROBLEM HERE

Microsoft JDBC Driver 4.2 for SQL Server  4.2.6420.100
Exception in thread "main" com.microsoft.sqlserver.jdbc.SQLServerException: com.microsoft.sqlserver.jdbc.SQLServerException: Incorrect syntax near ','.
    at com.microsoft.sqlserver.jdbc.SQLServerException.makeFromDriverError(SQLServerException.java:191)
    at com.microsoft.sqlserver.jdbc.SQLServerParameterMetaData.<init>(SQLServerParameterMetaData.java:423)
    at com.microsoft.sqlserver.jdbc.SQLServerPreparedStatement.getParameterMetaData(SQLServerPreparedStatement.java:1659)
    at CreateAMultiStationDailyLoadCtrAvgHistogram.main(CreateAMultiStationDailyLoadCtrAvgHistogram.java:68)
Java Result: 1

这是我的代码:

  prepStmt = buildPreparedStatement( conn.getConnectionObject() );  //function below
  conn.printDriverInfo();
  sqlDate = new java.sql.Date( beginDate.getTimeInMillis() );
  ParameterMetaData pmData = prepStmt.getParameterMetaData();
  System.out.println( "Parameter Count = " + pmData.getParameterCount() );
  prepStmt.setDate( 1, sqlDate );

  for( i = 0; i < locID.size(); i++ )
  {
    prepStmt.setString( ( i + 2 ), locID.get(i) );
  }

  rslt = prepStmt.executeQuery();

  private PreparedStatement buildPreparedStatement(java.sql.Connection con)
  throws SQLException
  {
    int i;
    StringBuilder sb = new StringBuilder();
    sb.append("SELECT AVG( ( High_Temperature + Low_Temperature ) / 2.0 ) ");
    sb.append("FROM obs_masterAll ");
    sb.append("WHERE Observation_Valid_Time = ? AND " );
    sb.append("Location_ID IN ( " );

    for( i = 0; i < ( locID.size() - 1 ); i++ )
    {
      sb.append( "?" ).append(", ");
    }

    sb.append( "?" ).append(" );");
    System.out.println( sb.toString() );
    return( con.prepareStatement( sb.toString() ) );
  }

问题是我的代码还是JDBC驱动程序?

2 个答案:

答案 0 :(得分:2)

我想说这是你使用的JDBC驱动程序版本中的一个问题。

我可以使用与您相同版本的SQL Server JDBC驱动程序重现此问题。我无法重现这个问题,针对MySQL和Oracle运行相同的查询。我不得不从查询末尾删除分号以使其针对Oracle运行,但同样的更改并不能解决SQL Server的问题。

如果我使用community technology preview edition of version 6.0 of the Microsoft JDBC driver(版本6.0.6629.101),我也无法重现此问题。

答案 1 :(得分:0)

上面关于JDBC驱动程序的回应让我接近了。我使用的是非常旧的Microsoft JDBC驱动程序,因此升级肯定有帮助。我现在正在使用Microsoft JDBC驱动程序6.0版的社区技术预览版(版本6.0.6629.101),而不是上面推荐的。

然而,我仍然遇到了问题。

当我从代码中删除以下行时:

ParameterMetaData pmData = prepStmt.getParameterMetaData();
System.out.println( "Parameter Count = " + pmData.getParameterCount() );

一切都按预期工作!

我不确定为什么'ParameterMetaData'数据类型不起作用,但是当从代码中删除时,它肯定解决了我的问题。

固定!