Sql 将表中的列别名插入查询结果
我有两个表,A1存储标准描述映射,B1存储每个标准的值。我希望使用A1映射中的列别名对B1表进行查询(结果查询),如下图所示Sql 将表中的列别名插入查询结果,sql,sql-server,Sql,Sql Server,我有两个表,A1存储标准描述映射,B1存储每个标准的值。我希望使用A1映射中的列别名对B1表进行查询(结果查询),如下图所示 我建议你改变桌子的设计。这是一种糟糕的数据存储方式,它不遵循规范化规则。您需要另一个连接表来存储rownum的CR值 无论如何,若您需要为这些表编写查询,那个么将A1表连接到B1表3次,并从那个里获取descr 更新(也使用@gotqn-answer的PIVOT查询): 正如你所说,可能会有很多CR*列。。。我讨厌游标,但当你需要它时: DECLARE @columnNa
我建议你改变桌子的设计。这是一种糟糕的数据存储方式,它不遵循规范化规则。您需要另一个连接表来存储rownum的CR值 无论如何,若您需要为这些表编写查询,那个么将A1表连接到B1表3次,并从那个里获取descr 更新(也使用@gotqn-answer的PIVOT查询): 正如你所说,可能会有很多CR*列。。。我讨厌游标,但当你需要它时:
DECLARE @columnName VARCHAR(200),
@query VARCHAR(8000) = 'SELECT b.rownum ',
@joins VARCHAR(8000) = '',
@tmpColumnValue VARCHAR(100);
DECLARE @getDescr CURSOR
SET @getDescr = CURSOR FOR
select name
from sys.columns where object_name(object_id) = 'B1' ANd name like 'CR%'
OPEN @getDescr
FETCH NEXT
FROM @getDescr INTO @columnName
WHILE @@FETCH_STATUS = 0
BEGIN
SELECT @tmpColumnValue = pr_desc FROM A1 WHERE pr_id = @columnName;
SET @query = @query + ', b.' + @columnName + ' AS ' + @tmpColumnValue;
PRINT @columnName
FETCH NEXT
FROM @getDescr INTO @columnName
END
CLOSE @getDescr
DEALLOCATE @getDescr
SET @query = @query + ' FROM B1 b ';
EXECUTE (@query)
使用PIVOT进行查询:
DECLARE @Descriptions VARCHAR(MAX);
DECLARE @columns VARCHAR(MAX);
SELECT @Descriptions = STUFF
(
(
SELECT ',[' + [pr_desc] + ']'
FROM A1
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)')
,1
,1
,''
)
SELECT @columns = STUFF
(
(
SELECT ',[' + [name] + ']'
FROM sys.columns
WHERE object_name(object_id) = 'B1' ANd name like 'CR%'
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)')
,1
,1
,''
)
SET @query = '
SELECT *
FROM
(
SELECT [rownum]
,[value]
,[pr_desc]
FROM B1
UNPIVOT
(
[value] FOR [column] IN (' + @columns + ')
) PVT
INNER JOIN A1 DS
ON PVT.[column] = DS.[pr_id]
) PVT
PIVOT
(
MAX([value]) FOR [pr_desc] IN (' + @Descriptions + ')
) PVT;
';
EXEC (@query)
在T-SQL的上下文中,可以按照以下步骤进行:
DECLARE @A1 TABLE
(
[pr_id] CHAR(3)
,[pr_desc] VARCHAR(12)
);
DECLARE @B1 TABLE
(
[rownum] TINYINT
,[name] VARCHAR(12)
,[Date] DATE
,[CR1] INT
,[CR2] INT
,[CR3] INT
);
INSERT INTO @A1 ([pr_id], [pr_desc])
VALUES ('CR1', 'Desc1')
,('CR2', 'Desc2')
,('CR3', 'Desc3');
INSERT INTO @B1 ([rownum], [name], [Date], [CR1], [CR2], [CR3])
VALUES (1, 'Jon', '1/1/2017', 10, 50, 100)
,(2, 'Jon', '2/1/2017', 60, 100, 500);
SELECT *
FROM @B1
UNPIVOT
(
[value] FOR [column] IN ([CR1], [CR2], [CR3])
) PVT;
@A1
表以获取描述:
SELECT *
FROM @B1
UNPIVOT
(
[value] FOR [column] IN ([CR1], [CR2], [CR3])
) PVT
INNER JOIN @A1 DS
ON PVT.[column] = DS.[pr_id];
UNPIVOT
和PIVOT
我们有很多硬编码值。因此,最好改用动态T-SQL
CREATE TABLE A1
(
[pr_id] CHAR(3)
,[pr_desc] VARCHAR(12)
);
CREATE TABLE B1
(
[rownum] TINYINT
,[name] VARCHAR(12)
,[Date] DATE
,[CR1] INT
,[CR2] INT
,[CR3] INT
);
INSERT INTO A1 ([pr_id], [pr_desc])
VALUES ('CR1', 'Desc1')
,('CR2', 'Desc2')
,('CR3', 'Desc3');
INSERT INTO B1 ([rownum], [name], [Date], [CR1], [CR2], [CR3])
VALUES (1, 'Jon', '1/1/2017', 10, 50, 100)
,(2, 'Jon', '2/1/2017', 60, 100, 500);
DECLARE @DynamicTSQLStatement NVARCHAR(MAX);
DECLARE @Descriptions NVARCHAR(MAX);
SELECT @Descriptions = STUFF
(
(
SELECT ',[' + [pr_desc] + ']'
FROM A1
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)')
,1
,1
,''
)
SET @DynamicTSQLStatement = '
SELECT *
FROM
(
SELECT [rownum]
,[value]
,[pr_desc]
FROM B1
UNPIVOT
(
[value] FOR [column] IN ([CR1], [CR2], [CR3])
) PVT
INNER JOIN A1 DS
ON PVT.[column] = DS.[pr_id]
) PVT
PIVOT
(
MAX([value]) FOR [pr_desc] IN (' + @Descriptions + ')
) PVT;
';
EXEC sp_executesql @DynamicTSQLStatement;
DROP TABLE A1;
DROP TABLE B1;
你可以用这个
DECLARE @COLNAMES VARCHAR(4000) =
CONVERT(VARCHAR(4000),
(SELECT * FROM (VALUES(NULL) ) AS X(DUMY)
LEFT JOIN B1 ON 1= 0
FOR XML RAW, ELEMENTS XSINIL ) )
SET @COLNAMES =
REPLACE(REPLACE(REPLACE(REPLACE(REPLACE(@COLNAMES,'<row xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">','')
, '<DUMY xsi:nil="true"/>','')
, ' xsi:nil="true"/><',', ')
, ', /row>','')
, '<','')
SELECT
@COLNAMES = REPLACE(@COLNAMES, pr_id, pr_id + ' ['+ pr_desc+ ']')
FROM A1
DECLARE @Query NVARCHAR(4000) = 'SELECT ' + @COLNAMES + ' FROM B1'
PRINT @Query
EXEC sp_executesql @Query
结果:
rownum Name Date Desc1 Desc2 Desc3
----------- -------------------------------------------------- -------------------- ----------- ----------- -----------
1 Jon 1/1/2017 10 50 100
2 Jon 2/1/2017 60 100 500
我想要一个查询…,您尝试了什么查询?谢谢您的建议,但无法重新设计表。还有一件事,在我的项目中,我有3个以上的标准(15),查询结果顺序是CR1、CR10、CR11。。。。。。。我应该在哪里对存储过程进行排序以更正排序(CR1、CR2…)?然后需要使用游标并遍历所有列并构建查询
SELECT rownum, Name, Date, CR1 [Desc1], CR2 [Desc2], CR3 [Desc3] FROM B1
rownum Name Date Desc1 Desc2 Desc3
----------- -------------------------------------------------- -------------------- ----------- ----------- -----------
1 Jon 1/1/2017 10 50 100
2 Jon 2/1/2017 60 100 500