Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/postgresql/10.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 如何设置已准备语句的参数列表?_Java_Postgresql_Jdbc_Prepared Statement - Fatal编程技术网

Java 如何设置已准备语句的参数列表?

Java 如何设置已准备语句的参数列表?,java,postgresql,jdbc,prepared-statement,Java,Postgresql,Jdbc,Prepared Statement,我有一份名单,例如: List<String> names = ... names.add('charles'); ... 如何执行以下操作: stmt.setParameterList(1,names); 有解决办法吗?有人能解释为什么缺少这种方法吗 使用:java、postgresql、jdbc3在我所知道的PreparedStatement上设置一个列表,是无法做到这一点的 编写代码,用适当数量的问号(与列表中的数字相同)构造SQL语句(或更好地替换单个?或类似标记)然后遍

我有一份名单,例如:

List<String> names = ...
names.add('charles');
...
如何执行以下操作:

stmt.setParameterList(1,names);
有解决办法吗?有人能解释为什么缺少这种方法吗


使用:java、postgresql、jdbc3

在我所知道的
PreparedStatement
上设置一个列表,是无法做到这一点的


编写代码,用适当数量的问号(与列表中的数字相同)构造SQL语句(或更好地替换单个?或类似标记)然后遍历列表,为每个设置参数。

由于类型擦除,此方法丢失。列表的参数类型在运行时丢失。因此,需要添加几种方法:
setIntParameters
setLongParameters
setObjectParameters
,等等。对于postgres 9,我使用了这种方法:

 jdbcTemplate.query(getEmployeeReport(), new PreparedStatementSetter() {
        @Override
        public void setValues(PreparedStatement ps) throws SQLException {
            ps.setTimestamp(1, new java.sql.Timestamp(from.getTime()));
            ps.setTimestamp(2, new java.sql.Timestamp(to.getTime()));
            StringBuilder ids = new StringBuilder();
            for (int i = 0; i < branchIds.length; i++) {
                ids.append(branchIds[i]);
                if (i < branchIds.length - 1) {
                    ids.append(",");
                }
            }
            // third param is inside IN clause
            // Use Types.OTHER avoid type check while executing query  
            ps.setObject(3, ids.toString(), **Types.OTHER**);
        }
    }, new PersonalReportMapper());
jdbcTemplate.query(getEmployeeReport(),new PreparedStatementSetter()){
@凌驾
public void setValues(PreparedStatement ps)引发SQLException{
ps.setTimestamp(1,新的java.sql.Timestamp(from.getTime());
ps.setTimestamp(2,新的java.sql.Timestamp(to.getTime());
StringBuilder ID=新的StringBuilder();
for(int i=0;i
今天早上我正在查看代码,我的一位同事有一种不同的方法,只需使用
setString(“name1'、'name2'、'name3')传递参数即可。


注意:我跳过了开头和结尾的单引号,因为它们将由
设置字符串添加

这个问题很老了,但是没有人建议使用

这个答案可能有助于其他方法:

public void setValues(PreparedStatement ps) throws SQLException {
    // first param inside IN clause with myList values
    ps.setObject(1 , myList.toArray(), 2003); // 2003=array in java.sql.Types
}

在不同的论坛上检查了各种解决方案,但没有找到一个好的解决方案后,我觉得下面我提出的破解方法是最容易遵循和编写的。但是请注意,这并不使用准备好的查询,而是完成了工作:

示例:假设您有一个参数列表要在'in'子句中传递。只需在'IN'子句中放入一个伪字符串,例如,“PARAM”表示将取代该伪字符串的参数列表

    select * from TABLE_A where ATTR IN (PARAM);
可以将所有参数收集到Java代码中的单个字符串变量中。这可以通过以下方式完成:

    String param1 = "X";
    String param2 = "Y";
    String param1 = param1.append(",").append(param2);
在本例中,您可以将所有由逗号分隔的参数附加到单个字符串变量“param1”中

在将所有参数收集到一个字符串中之后,您只需将查询中的伪文本(在本例中为“PARAM”)替换为参数字符串(即param1)。以下是您需要做的:

    String query = query.replaceFirst("PARAM",param1); where we have the value of query as 

    query = "select * from TABLE_A where ATTR IN (PARAM)";

现在可以使用executeQuery()方法执行查询。只要确保你的查询中没有“PARAM”这个词。您可以使用特殊字符和字母的组合,而不是单词“PARAM”,以确保查询中不可能出现此类单词。希望您能找到解决方案。

如果问题的意思是在一次调用中设置多个参数

因为类型验证已经在更高的级别上定义了,所以我认为唯一需要的是

因此,可以使用实用方法:

public static void addParams(PreparedStatement preparedStatement, Object... params) throws SQLException {
    for (int i = 0; i < params.length; i++) {
        Object param = params[i];
        preparedStatement.setObject(i+1, param);
    }
}

请随意将其转换为Java 8 lambda:)

如果每个数据类型都有一个add方法,为什么每个数据类型都没有一个“addList”方法呢?(例如addStringList(…))这就是问题所在,即使不计算列表变量,语句接口也已经膨胀。类型擦除不是一个好的原因,对于常量字符串可能有setArrayParameter(int-pos,Object[]params),这可能是可以接受的。对于用户输入,这是一个很好的例子,说明代码容易受到SQL注入的攻击。这绝对不应该起作用。如果是这样,您的JDBC驱动程序中就有一个bug
setString
处理撇号,这样您就可以实际获得传递的
String
。你的同事测试过他们的代码吗?请对你的代码做一些解释这真的有效吗?你知道这可能会导致SQL注入吗?谢谢它有效…:)这真的适用于(?)
中的
?一旦将实际语句发布到服务器,它会是什么样子?您希望避免在JDBC代码中串接字符串值,因为这很容易导致SQL注入错误-1setObject传递一个列表会引发Oracle driversetArray的异常。由于MySQL或JavaDB不支持SQL中的数组数据类型,因此它无法与MySQL或JavaDB一起使用。请参阅顶部的注释:@TigerC10好点。。。好奇激起了re:Java内存中数据库-Derby(JavaDB)不支持,但同时支持和。
public static void addParams(PreparedStatement preparedStatement, Object... params) throws SQLException {
    for (int i = 0; i < params.length; i++) {
        Object param = params[i];
        preparedStatement.setObject(i+1, param);
    }
}
SqlUtils.addParams(preparedStatement, 1, '2', 3d);