加入两个表,其中一个表有行到列

时间:2015-07-27 12:04:56

标签: sql .net sql-server

我有一个具有这种结构的表:

Table 1: ID(PK) | <other columns>
              1 | otherdata
              2 | otherdata

另一张表,它是一个包含要下载的URL的文档列表(PDF,DOC等)。这些文件存储在我的网络中。

Table 2: ID | IDDOC |    LINKDOC    | INFO
          1 |   1   | 'http://URL1' | 'Info1'
          1 |   2   | 'http://URL2' | 'Info2'
          2 |   1   | 'http://URL3' | 'Info3'

ID是表1的外键,IDDOC是描述文档类型的第3个表(下面)的外键:

Table 3: IDDOC | Name
            1  | 'Contract'
            2  | 'Notification'

我需要生成一个查询来连接这些表并获得类似的结构

ID | <SomeCollumsTable1> | NameDesc1 | NameURL1 | ... | NameDesc2 | NameURL2

示例输出:

  ID | <SomeCollumsTable1> | ContractDesc | ContractURL   | NotificationDesc | NotificationURL
  1  | otherdata           | 'Info1'      | 'http://URL1' | 'Info2'          | 'http://URL2'
  2  | otherdata           | 'Info3'      | 'http://URL3' | ''               | ''

即。在“Table3”中生成许多对描述/ URL,因为有多个记录退出。样本数据有2种文档类型,并生成4列。

目前我对每个所需的文档都有subquerys,但对我来说效率非常低,查询很大,我在“Table3”中添加的新文档需要在整个查询中进行更改,只需要调整Where子句来指示为什么IDDOC需要。 (使用IN子句)

或者最好在我的应用程序中操作它(winforms / vb.net)?

该应用程序以EXCEL格式生成报告。

1 个答案:

答案 0 :(得分:1)

请尝试以下查询:

DECLARE @qu NVARCHAR(MAX), @pcol NVARCHAR(MAX)
SELECT   @pcol= COALESCE(@pcol + ',','') + type FROM
 (SELECT Name+N'URL' AS type FROM t3 UNION SELECT Name+N'Desc' AS type FROM t3 ) A

SET @qu=N'Select ID,b,c,'+ @pcol + N' FROM
  (
    SELECT t1.ID, t1.b,t1.c, t2.linkdoc as data,t3.Name +N''URL'' as Type FROM t1 LEFT JOIN t2 ON t1.ID=t2.ID
    LEFT JOIN t3 ON t2.iddoc=t3.iddoc
    UNION
    SELECT t1.ID, t1.b, t1.c, t2.info as data, t3.Name +N''Desc'' as Type FROM t1 LEFT JOIN t2 ON t1.ID=t2.ID
    LEFT JOIN t3 ON t2.iddoc=t3.iddoc
  )S
  PIVOT
  (
  MAX(data) 
    FOR Type IN ('+@pcol +N')) AS piv'
EXEC sp_executesql @qu

这是一个sql小提琴: http://sqlfiddle.com/#!6/9fb46/1

  

编辑:已添加解释

     

所以基本上我使用PIVOT,除了PIVOT可以在a上完成   在我们的示例中,单列,位于URLDesc列。但我们   需要两个这些列都可以旋转,所以我使用了UNION来进入   单列data,如下所示

SELECT t1.ID, t1.b,t1.c, t2.linkdoc as data,t3.Name +N'URL' as Type FROM t1 LEFT JOIN t2 ON t1.ID=t2.ID
LEFT JOIN t3 ON t2.iddoc=t3.iddoc
UNION
SELECT t1.ID, t1.b, t1.c, t2.info as data, t3.Name +N'Desc' as Type FROM t1 LEFT JOIN t2 ON t1.ID=t2.ID
LEFT JOIN t3 ON t2.iddoc=t3.iddoc
     

然后我在PIVOT中使用了这样的:

Select ID,b,c,[ContractURL],[ContractDesc],[NotificationURL],[NotificationDesc]
FROM
  (
      SELECT t1.ID, t1.b,t1.c, t2.linkdoc as data,t3.Name +N'URL' as Type FROM t1 LEFT JOIN t2 ON t1.ID=t2.ID
  LEFT JOIN t3 ON t2.iddoc=t3.iddoc
  UNION
  SELECT t1.ID, t1.b, t1.c, t2.info as data, t3.Name +N'Desc' as Type FROM t1 LEFT JOIN t2 ON t1.ID=t2.ID
  LEFT JOIN t3 ON t2.iddoc=t3.iddoc
  )S
  PIVOT
  (
  MAX(data) 
    FOR Type IN ([ContractURL],[ContractDesc],[NotificationURL],[NotificationDesc])
  )piv 
     

现在,为了实现这种动态,我计算了表t3中的所有唯一列,如

SELECT Name+N'URL' AS type FROM t3 UNION SELECT Name+N'Desc' AS type FROM t3