PreparedStatement.setString()调用表现得很奇怪

时间:2011-03-14 19:41:58

标签: java sql

这可能很简单,但我不明白出了什么问题。

作为背景,我将PreparedStatements与模板查询一起使用以提高效率。我调用setString(index,argument)来填充模板的各个部分,在填充所有字段之后,我调用execute语句。

以下是目前情况的片段(当然还有效):

   stmnt.setInt(1, node.getI_ID());
   stmnt.setString(2, node.getTime());
   stmnt.setInt(3, node.getMemoryAddress());
   stmnt.executeUpdate();

getI_ID返回一个5位数的int数,如10014,与getMemoryAddress相同。 getTime返回日期时间,如“2011-03-14_13:23:00”。

目标是当查询最终执行该日期时间的小时但增加1时,但是我不能修改从getTime返回的值这一事实,即这应该通过添加一些来完成快速而又脏的SQL代码。

这是我最初想出的:

   stmnt.setInt(1, node.getI_ID());
   stmnt.setString(2, node.getTime() + " interval 1 hour");
   stmnt.setInt(3, node.getMemoryAddress());
   stmnt.executeUpdate();

但是,执行时,getTime的未修改值应该在我新添加的行中。当PreparedStatement将String转换为VARCHAR或DATETIME时,是否存在适用的字符串条件?或者字符串可能不包含多个标记或其他内容?

此外,我无法在查询模板中添加“间隔1小时”,因为并非所有节点都需要添加一小时。

非常感谢任何帮助。感谢。

2 个答案:

答案 0 :(得分:5)

声明

   stmnt.setString(2, node.getTime() + " interval 1 hour");

字符串连接发生在Java中,而不是SQL中。如果node.getTime()返回,比如“2011-03-14_13:23:00”,则在setString()中发送以下值:

"2011-03-14_13:23:00 interval 1 hour"

这可能不是你想要的。 “间隔1小时”不会修改SQL,它是SQL语句的的一部分。

如果要将小时增加1,则应将字符串值解析为GregorianCalendar,在那里增加小时,然后格式化结果并将其发送到SQL语句。例如:

    DateFormat df = new SimpleDateFormat("yyyy-MM-dd_HH:mm:ss");
    String input = "2011-03-14_13:23:00";
    Date d = df.parse(input);
    GregorianCalendar c = new GregorianCalendar();
    c.setTime(d);
    c.add(Calendar.HOUR_OF_DAY, 1);
    String output = df.format(c.getTime());

答案 1 :(得分:2)

除了吉姆加里森所说的话:

不要将setString()用于日期或时间戳列。

使用setDate()setTimestamp()代替java.sql.Date或java.sql.Timestamp的实例。

通过这种方式,您可以屏蔽任何可能根据客户端和数据库的NLS设置而有所不同的字符串到日期转换。传递第一类日期或时间戳对象很多更安全。