Sql server 从逗号分隔的ID列表返回逗号分隔的名称列表

Sql server 从逗号分隔的ID列表返回逗号分隔的名称列表,sql-server,coldfusion,Sql Server,Coldfusion,首先,请不要对我持有糟糕的数据库结构。我们都有不能更改的必须处理的事情,我继承了这些在应用程序中根深蒂固的表 考虑以下两个表: Personnel +-----+-------+--------------+ | ID | Name | TECHNIQUE_ID | +-----+-------+--------------+ | 134 | Bob | 1,2,4 | +-----+-------+--------------+ | 135 | Mary | 1,3,4

首先,请不要对我持有糟糕的数据库结构。我们都有不能更改的必须处理的事情,我继承了这些在应用程序中根深蒂固的表

考虑以下两个表:

Personnel
+-----+-------+--------------+
| ID  | Name  | TECHNIQUE_ID |
+-----+-------+--------------+
| 134 | Bob   | 1,2,4        |
+-----+-------+--------------+
| 135 | Mary  | 1,3,4        |
+-----+-------+--------------+
| 136 | Frank | 2            |
+-----+-------+--------------+

Techniques
+-----+----------+
| ID  | Name     |
+-----+----------+
| 1   | Fishing  |
+-----+----------+
| 2   | Archery  |
+-----+----------+
| 3   | Bowling  |
+-----+----------+
| 4   | Hiking   |
+-----+----------+
我需要的是每个人的列表,以及他们执行的技术的逗号分隔列表。基本上把“1,3,4”变成“钓鱼、保龄球、徒步旅行”


我可以通过使用嵌套查询在CF代码中实现这一点,但是报告有数千行。。。这意味着它可能只为一份报告运行数万个查询。我更喜欢在一个查询中完成所有操作。

执行两个单独的查询,一个是
人员表,另一个是
技术表

将查询结果处理为关联数组,其中索引是ID,值是名称


输出personal.technology_ID字段时,将逗号分隔的值作为列表处理。循环遍历列表中的每个项目,并输出技术关联数组的值。

您可以使用
之类的方法进行连接:

select p.*
from Personnel p join
     Techniques t
     on ','+ p.TECHNIQUE_ID+',' like '%,'+cast(t.id as varchar(255))+',%'

您真的需要将其作为串联字符串吗?或者单独的行足够好吗?

更新

另一种可能是将类似Gordon的代码和组合在一起,在一个查询中返回所有内容。(我怀疑其中任何一个都会是速度恶魔,拥有非常大的表,但考虑到您继承的模式,这是意料之中的。)


(这不是一个完整的答案,但太长了,无法评论……)

如果仅显示信息,则可以与分组的
cfoutput
组合以生成所需的输出。(只需确保对结果进行排序
personal.name
然后再排序
technologies.name

代码:

<cfoutput query="yourQuery" group="id">
    <cfset skills = []>
    <cfoutput>
        <cfset arrayAppend(skills, skillTitle)>
    </cfoutput>

    NAME: #name# | 
    SKILLS: #arrayToList(skills)#<br>
</cfoutput>
NAME: Bob   | SKILLS: Archery,Fishing,Hiking
NAME: Frank | SKILLS: Archery
NAME: Mary  | SKILLS: Bowling,Fishing,Hiking

如果您使用的是ColdFusion,那么为什么不使用1个普通的DB查询,并使用分组输出或“查询查询”将结果合并到一个逗号分隔的列表中呢?我在上一段中提到过。基本上,仅使用逗号分隔ID的结果就有数千条记录,每个逗号分隔列表中最多有20项。因此,对于一个查询的查询,我将在每个页面加载时访问数据库20000次。不理想。解决方案可能在于将技术存储在本地数组中,然后在到达每个逗号分隔的列表时循环(而不是再次命中数据库)。“query of query”不会再次命中数据库。它在内存中搜索查询结果结构。仅供参考,“查询的查询”与嵌套查询不同。“查询的查询”是指
dbtype
参数等于
query
。在您的查询中没有类似于
的查询。我在循环方面做了一些努力(因为我在循环中有一个cfoutput标记),但一旦我简化了它,它就非常有效。谢谢
NAME: Bob   | SKILLS: Archery,Fishing,Hiking
NAME: Frank | SKILLS: Archery
NAME: Mary  | SKILLS: Bowling,Fishing,Hiking