我希望能够向UNION查询未知数量的记录集。但是,在记录集名称中不允许执行查询查询点或括号时。
例如,这失败了:
<cfquery name="allRecs" dbtype="query">
SELECT * FROM recordset[1]
UNION
SELECT * FROM recordset[2]
</cfquery>
使用动态变量名称,例如“recordset1”工作,但这是在一个函数中,需要变量范围,所以我不能动态地建立变量名,而不会在持久化对象中产生内存泄漏。
还有其他想法吗?
答案 0 :(得分:2)
在发布问题后,我提出了几个解决方案,但可能会有一个更好的解决方案
我可以将动态命名变量写入参数范围,然后引用它们而不在查询范围内
创建一个接受2个记录集作为参数的函数,并返回一个组合记录集。这可以循环以逐步添加记录集。我确信与在一个查询中执行所有UNION相比,这是非常低效的。
答案 1 :(得分:1)
艰巨的任务。我可以想象使用基于GetColumnNames()
的嵌套循环的解决方案,使用QueryAddRow()
和QuerySetCell()
。它不是最有效的,但它并不是很慢。当然,取决于任务的大小。
当你创建它以接受十个参数时,你的“创建一个结合了两个记录集的函数”可以变得更有效率。动态修改SQL:
<cfset var local = StructNew()>
<cfquery name="local.union" dbtype="query">
SELECT * FROM argument1
<cfloop from="2" to="#ArrayLen(arguments)#" index="local.i">
<cfif IsQuery(arguments[local.i])>
UNION
SELECT * FROM argument#local.i#
</cfif>
</cfloop>
</cfquery>
<cfreturn local.union>
答案 2 :(得分:1)
经过一番快速的探索,我发现了这个: queryConcat来自CFLib.org。它使用queryaddrow / querysetcell来连接两个查询。
我添加了一个快速功能(没有错误检查或数据验证,因此我不会按原样使用它):
<cffunction name="concatenate">
<cfset var result = arguments[1]>
<cfloop from="2" to="#arraylen(arguments)#" index="i">
<cfset result=queryconcat(result, arguments[i])>
</cfloop>
<cfreturn result>
</cffunction>
作为测试,我把它扔在一起:
事实上,这给了你fred / sammy / fred。
这可能不是最有效的实现,但您可以随时更改插入/联合代码,以便在需要时更快。大多数情况下,我的目标是尽可能少地编写代码。 : - )
答案 3 :(得分:1)
此处添加的所有解决方案都应该适合您,但我还要提到,根据您使用的数据量和您使用的数据库,您可能最好尝试找到一种方法来执行此操作数据库方面。对于非常大的记录集,将记录写入临时表并再次选择它们可能是有益的,但无论哪种方式,如果您可以以任何方式重写查询以让数据库首先处理此问题,您将是更好。