因此,我在C#中有一个Winforms项目需要生成正确的SQL并使用odp.net将其发送到数据库。我可以处理执行字符串操作等的C#部分,但实际查询需要正确。
不幸的是,我在SQL中的培训实际上是针对Microsoft T-SQL的。 ' in'声明对我来说有点新鲜。
因此,当我尝试查询的某些不同变体时,我得到了不同的结果。我需要知道为什么以及我能做些什么来获得正确的结果。
所以这是SQL代码的一种变体。
SELECT o.rid,
o.tcode,
o.dwave_id,
o.cvarid,
r.pmid
FROM STREADM.router_opport o, SPROADM.RESP r
WHERE o.tcode in (&touch_codes)
and o.rid = r.rid
AND is_active = 'Y'
ORDER BY rid;
当在PL / SQL开发人员中运行上述代码然后手动输入触摸代码的值时,会给出绝对正确的结果。
然而,当我尝试自动化时,我需要生成代码。我遇到了两个问题。第一个是in子句的1000限制。另一个是奇怪的结果。那么上面的代码和这段代码之间会有什么不同呢?
SELECT o.rid,
o.tcode,
o.dwave_id,
o.cvarid,
r.pmid
FROM STREADM.router_opport o, SPROADM.RESP r
WHERE o.tcode in ('code1','code2')
OR o.tcode in ('code3','code4')
and o.rid = r.rid
AND is_active = 'Y'
ORDER BY rid;
这与下面有什么不同吗?
SELECT o.rid,
o.tcode,
o.dwave_id,
o.cvarid,
r.pmid
FROM STREADM.router_opport o, SPROADM.RESP r
WHERE o.tcode ='code1'
OR o.tcode ='code2'
OR o.tcode ='code3'
OR o.tcode ='code4'
and o.rid = r.rid
AND is_active = 'Y'
ORDER BY rid;
基本上我需要知道并理解SQL代码会产生与第一段代码完全相同的结果。
答案 0 :(得分:2)
WHERE o.tcode ='code1'
OR o.tcode ='code2'
OR o.tcode ='code3'
OR o.tcode ='code4'
在语义上完全等同于
WHERE o.tcode in('code1', 'code2', 'code3', 'code4')
和
WHERE o.tcode in('code1', 'code2')
OR o.tcode in('code3', 'code4')
话虽这么说,我会对任何涉及使用硬编码文字生成SQL语句而不是绑定变量的解决方案或任何生成IN
列表超过1000个元素的解决方案感到怀疑。这些元素来自哪里?它们来自查询吗?您可以将它们加载到临时表或集合中,并在select
语句中引用该临时表/集合吗?
答案 1 :(得分:2)
你说
“我遇到了两个问题.....另一个是奇怪的结果。”
由于条件优先级,您的第二组查询将不会产生与原始查询相同的结果。 Find out more.
简而言之,您大肆混合OR和AND子句,而Oracle并没有按照您的想法对它们进行评估。您需要做的是将所有OR子句包装在一组外部括号中,以向Oracle展示如何评估条件。所以...
WHERE
(
o.tcode in ('code1','code2')
OR o.tcode in ('code3','code4')
)
and o.rid = r.rid
AND is_active = 'Y'
......或......
WHERE
(
o.tcode ='code1'
OR o.tcode ='code2'
OR o.tcode ='code3'
OR o.tcode ='code4'
)
and o.rid = r.rid
AND is_active = 'Y'
“输入是从excel文件中读取的。”
从这样的源导入数据的最佳方法是将其作为CSV文件从Excel导出(提供数据的源系统可能能够以此格式生成数据)然后使用外部表来将数据公开给数据库。 Find out more