我确实从这个问题PreparedStatement IN clause alternatives?中读到了解决方案。但就我而言,我在一个In子句中有大约5000个参数,它会导致java.sql.SQLException:Prepared或callable语句有超过2000个参数标记。
我使用的是像
这样的SQLString sql = "select * from project in " + projectIds.toString()
projectIds
是一个StringBuilder,就像“(1,2,3,4 ......)”但是代码安全报告说它可能导致sql注入。所以我必须使用?占位符以避免它。
我尝试使用
String sql = "select * from project where charindex(','+convert(varchar(max),id)+',', ?)>0";
statement.setString(1,projectIds.toString);//projectIds like ",1,2,3,4,"..
但最终会出现错误的语法错误。
有没有解决方案?
答案 0 :(得分:2)
Hogan建议使用表格是一个很好的建议。我唯一要改变的是查询,因为JOIN
为tablelist中的每个值生成一行。相反(猜测你的列名)
select * from project
where projectID in (select id from tablelist)
或
where exists (select 1 from tablelist where id = projectID)
答案 1 :(得分:1)
执行此操作的最佳方法是不使用in语句。相反,您应该将要检查的所有值放在表中并使用连接。
例如,如果您有一个包含列的表(名为id)的表,那么您的语句将如下所示:
select *
from project
join tablelist on project.project = tablelist.id
这会快得多,因为SQL服务器非常擅长快速执行连接。
您也可以使用CTE执行此操作。例如:
WITH tablelist as
(
SELECT 1 AS id
UNION ALL
SELECT 3
UNION ALL
SELECT 4
UNION ALL
SELECT 5
UNION ALL
SELECT 6
UNION ALL
SELECT 7
// More if needed
)
select *
from project
join tablelist on project.project = tablelist.id
这可以作为一个大查询发送并且可以工作。你的唯一限制是查询的最大大小,我不知道是否存在这样的限制。
答案 2 :(得分:1)
select * from project in " + projectIds.toString()
语法不正确,应该是
select * from project where id in (" + projectIds + ")";