Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/72.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 不带引号的PreparedStatement.setString()方法_Java_Sql_Jdbc_Prepared Statement - Fatal编程技术网

Java 不带引号的PreparedStatement.setString()方法

Java 不带引号的PreparedStatement.setString()方法,java,sql,jdbc,prepared-statement,Java,Sql,Jdbc,Prepared Statement,我正在尝试使用一个PreparedStatement,其代码类似于: SELECT * FROM ? WHERE name = ? 显然,当我使用setString()设置表和名称字段时会发生以下情况: SELECT * FROM 'my_table' WHERE name = 'whatever' 而且查询不起作用。有没有一种方法可以设置不带引号的字符串,使行看起来像这样: SELECT * FROM my_table WHERE name = 'whatever' 或者我应该放弃它,改

我正在尝试使用一个PreparedStatement,其代码类似于:

SELECT * FROM ? WHERE name = ?
显然,当我使用setString()设置表和名称字段时会发生以下情况:

SELECT * FROM 'my_table' WHERE name = 'whatever'
而且查询不起作用。有没有一种方法可以设置不带引号的字符串,使行看起来像这样:

SELECT * FROM my_table WHERE name = 'whatever'

或者我应该放弃它,改为使用常规语句(参数来自系统的另一部分,这两个参数都不是用户输入的)?

参数不能用于参数化表或任何数据库对象。它们主要用于参数化WHERE/HAVING子句

要做您想做的事情,您需要自己进行替换,并根据需要创建一个常规语句


当您使用一个准备好的语句时,这是对数据库的一个提示,提示对该语句进行预先处理-例如,解析字符串并可能确定执行计划。如果查询中使用的对象可以动态更改,那么数据库就不能做很多前期准备。

不幸的是,您无法为准备好的语句参数化表名。如果需要,您可以构造一个字符串并将其作为动态SQL执行。

我怀疑您的SQL是否真的具有无限的灵活性。表的数量是有限的,因此表示所需SQL的静态最终字符串的数量也是有限的


继续使用PreparedStatement并绑定变量。这是完全值得的,特别是在避免SQL注入问题时非常有用。

您所犯的错误是,无法将表名作为参数传递。您应该只将值传递给SQL语句

例: 如果你想:

Select * from LoggedUsers where username='whatever' and privilege='whatever';
然后,您必须将PreparedStatement构建为:

Select * from LoggedUsers where username=? and privilege=?

setString(1, usernameObject);
setString(2, privilegeObject);
PreparedStatement的目的是降低数据库连接代码的难度和可读性。当开发人员必须在语句实例中使用如此多的列值时,很难使用分号、逗号和加号(concat运算符)


我认为您错误地想利用它,它不是设计为……

为了进一步说明这一点,并不是使用setString在字符串周围加引号,因为它不起作用(绑定变量不是这样工作的)。只是你不能在查询的这一部分使用变量。明白了,谢谢!如果参数不是用户输入的,那么在这里使用PreparedStatement没有多大意义?我的意思是,与使用常规语句相比,它的成本可能更高。或者我应该在任何地方使用PreparedStatement吗?您仍然可以使用PreparedStatement,只是不要尝试参数化表名-参数化“where”。关于准备和常规陈述的使用有一些争论,但是我相信,除非你发现好的理由,否则不要使用准备好的陈述。你正在考虑这样做的事实告诉我,你应该考虑重塑你的数据。也许您应该创建一个合并所有表的视图,添加一列作为“表名”。您显然没有足够的阅读Dailywtf.com。每个客户都有一个表(并且客户数量不受限制)是一种常用的反模式。显然不是。谢谢你的提醒。8) 这个答案的后半部分显然是错误的。准备好的语句是为了安全(即防止注入),而不是可读性。