Sql 子查询返回了多个值。内部查询

Sql 子查询返回了多个值。内部查询,sql,sql-server,sql-server-2008,Sql,Sql Server,Sql Server 2008,我有两张表tbl\u类别和tbl\u课程 在tbl_类别中我有如下行: CatID CatName CatDesc 1 Cat1 catDesc1 2 Cat2 catDesc2 3 Cat3 catDesc3 4 Cat4 catDesc4 5 Cat5 catDesc5 在tbl_课程中的值如下 CoursID Name AssignCategory AdditionalCat 1 cou1

我有两张表
tbl\u类别
tbl\u课程

tbl_类别中
我有如下行:

 CatID CatName CatDesc
  1     Cat1   catDesc1
  2     Cat2   catDesc2
  3     Cat3   catDesc3
  4     Cat4   catDesc4
  5     Cat5   catDesc5
tbl_课程中
的值如下

CoursID Name AssignCategory AdditionalCat
 1       cou1   1             2,3
 2       cou2   2               3
 3       cou3   1             3,4 
我需要的结果如下

包含AsignCategory和additionalcat的类别

 CatID CatName CatDesc
  1     Cat1   catDesc1
  2     Cat2   catDesc2
  3     Cat3   catDesc3
  4     Cat4   catDesc4
 CatID CatName CatDesc
  5     Cat5   catDesc5
不包含AsignCategory和additionalcat的类别

 CatID CatName CatDesc
  1     Cat1   catDesc1
  2     Cat2   catDesc2
  3     Cat3   catDesc3
  4     Cat4   catDesc4
 CatID CatName CatDesc
  5     Cat5   catDesc5
我正在使用这个分割函数

CREATE FUNCTION dbo.StrSplit (@sep char(1), @s varchar(512))  
RETURNS table  
AS  
RETURN (  
    WITH Pieces(pn, start, stop) AS (  
      SELECT 1, 1, CHARINDEX(@sep, @s)  
      UNION ALL  
      SELECT pn + 1, stop + 1, CHARINDEX(@sep, @s, stop + 1)  
      FROM Pieces  
      WHERE stop > 0  
    )  
    SELECT pn,  
      SUBSTRING(@s, start, CASE WHEN stop > 0 THEN stop-start ELSE 512 END) AS s  
    FROM Pieces  
  )  
我正在使用以下查询表单分配类别结果:

 select * from dbo.Tbl_Category
 where catid in(select assigncategory from Tbl_Course ) 

 )

 select * from dbo.Tbl_Category
 where catid not in(select assigncategory from Tbl_Course          
 )

请帮助我处理上述查询的其他类别结果。

您应该使用交叉应用来使用您的
StrSplit
udf:

SELECT * FROM dbo.tbl_Category
WHERE CatID IN(
    SELECT AssignCategory 
    FROM tbl_Course
    UNION
    SELECT CAST(split.S as int) 
    FROM tbl_Course
    CROSS APPLY dbo.StrSplit(',', AdditionalCat) as split )

SELECT * FROM dbo.tbl_Category
WHERE CatID NOT IN(
    SELECT AssignCategory 
    FROM tbl_Course
    UNION
    SELECT CAST(split.S as int) 
    FROM tbl_Course
    CROSS APPLY dbo.StrSplit(',', AdditionalCat) as split )
SQLFiddle


还可以使用UNPIVOT来避免使用UNION。但是,由于只有两列需要合并,因此UNION在这方面可能“足够好了”。

这里有一个基本的db设计问题,如果可以修改db设计,我会将课程和类别之间的链接分解成一个单独的表,如果它们可以分配给多个类别,而不是串联值。这将使您的查询更简单。错误消息在哪一行?为什么我们关心这个函数?@RandomUs1r:OP希望使用
StrSplit
函数将
AdditionalCat
的内容转换为以逗号分隔的类别ID列表。当然不是一个很好的模式,但这是可以做到的。有人做了neg标记,但他在sql方面非常差