如果你有自己的问题,问题更可能得到答案。 SO会帮助你解决代码错误和问题,但不是代码编写服务。
这就是说;它正好发生,我有一个工作的例子...
该示例使用您的示例记录,包装在一个表变量。表变量使得共享数据变得更容易,像SQL Fiddle和Stack Data Exchange这样的服务也是如此。如果让社区更容易帮助你,你更有可能得到答案。
示例数据
/* I've used a table variable to make
* sharing the example data easier.
*/
DECLARE @Table TABLE
(
cpf VARCHAR(11),
ddd INT,
phone VARCHAR(10),
[type] VARCHAR(1),
origin VARCHAR(10)
)
;
-- Demo values taken from OP.
INSERT INTO @Table
(
cpf,
ddd,
phone,
[type],
origin
)
VALUES
('11111111111', 83, '87472222', 'M', 'SERASA'),
('11111111111', 83, '81023333', 'M', 'TRANSUNION'),
('11111111111', 83, '88724444', 'M', 'TRANSUNION'),
('11111111111', 83, '87475555', 'M', 'TRANSUNION'),
('22222222222', 43, '36271111', 'F', 'SERASA'),
('22222222222', 44, '36272222', 'F', 'SERASA'),
('22222222222', 43, '36273333', 'F', 'TRANSUNION'),
('22222222222', 43, '36284444', 'F', 'TRANSUNION'),
('33333333333', 51, '51811111', 'F', 'SERASA'),
('33333333333', 51, '56212222', 'F', 'SERASA'),
('33333333333', 51, '96213333', 'M', 'SERASA')
;
要将您的行转换成列,我测序的记录。使用ROW_NUMBER我已经为每个cpf分配了第一个记录,第二个记录为第二个记录等等。为了避免无休止地重新输入ROW_NUMBER(),我将结果转换为common table expression。 CTE是创建临时可重用数据集的好方法。最后一步是将编号为1的记录移动到第一组列中,编号为2的记录到第二组中,等等。
将行移动到列中可能值得更详细的解释。我使用CASE expressions来根据ROW_NUMBER()返回的序列号条件移动值。然后我通过cpf GROUPED的结果。用MAX包装每个个案表达式将返回所需的结果。
CASEing行转换成列
/* The records from each cdp are numbered.
* The numbering is used to pivot the rows into
* columns.
*/
WITH Sequenced AS
(
-- This CTE numbers the records for each cpf.
SELECT
ROW_NUMBER() OVER (PARTITION BY cpf ORDER BY phone) AS rn,
*
FROM
@Table
)
SELECT
cpf,
-- First set of columns.
MAX(CASE WHEN rn = 1 THEN ddd ELSE NULL END) AS ddd_1,
MAX(CASE WHEN rn = 1 THEN phone ELSE NULL END) AS phone_1,
MAX(CASE WHEN rn = 1 THEN [type] ELSE NULL END) AS type_1,
MAX(CASE WHEN rn = 1 THEN origin ELSE NULL END) AS origin_1,
-- Second set of columns.
MAX(CASE WHEN rn = 2 THEN ddd ELSE NULL END) AS ddd_2,
MAX(CASE WHEN rn = 2 THEN phone ELSE NULL END) AS phone_2,
MAX(CASE WHEN rn = 2 THEN [type] ELSE NULL END) AS type_2,
MAX(CASE WHEN rn = 2 THEN origin ELSE NULL END) AS origin_2,
-- Third set of columns.
MAX(CASE WHEN rn = 3 THEN ddd ELSE NULL END) AS ddd_3,
MAX(CASE WHEN rn = 3 THEN phone ELSE NULL END) AS phone_3,
MAX(CASE WHEN rn = 3 THEN [type] ELSE NULL END) AS type_3,
MAX(CASE WHEN rn = 3 THEN origin ELSE NULL END) AS origin_3,
-- Fourth set of columns
MAX(CASE WHEN rn = 4 THEN ddd ELSE NULL END) AS ddd_4,
MAX(CASE WHEN rn = 4 THEN phone ELSE NULL END) AS phone_4,
MAX(CASE WHEN rn = 4 THEN [type] ELSE NULL END) AS type_4,
MAX(CASE WHEN rn = 4 THEN origin ELSE NULL END) AS origin_4
FROM
Sequenced
GROUP BY
cpf
;
结果
这是很多参加。让我们分解步骤。首先,CTE添加一个分区行号:
rn cpf ddd phone type origin
1 11111111111 83 81021111 M SERASA
2 11111111111 83 87472222 M SERASA
3 11111111111 83 81023333 M TRANSUNION
4 11111111111 83 88724444 M TRANSUNION
5 11111111111 83 87475555 M TRANSUNION
1 22222222222 43 36271111 F SERASA
2 22222222222 44 36272222 F SERASA
3 22222222222 43 36273333 F TRANSUNION
4 22222222222 43 36284444 F TRANSUNION
1 33333333333 51 51811111 F SERASA
2 33333333333 51 56212222 F SERASA
3 33333333333 51 96213333 M SERASA
接下来,case表达式根据行号将行移动到列中。我只包括一些列和行以方便阅读。
rn cpf phone_1 phone_2 phone_3
1 11111111111 81021111 NULL NULL
2 11111111111 NULL 87472222 NULL
3 11111111111 NULL NULL 87475555
最后,分组将删除多余的行。最大功能优于空值的内容。我再次删除了行和列,以便更容易遵循。
rn cpf phone_1 phone_2 phone_3
1 11111111111 81021111 87472222 87475555
2 22222222222 36271111 36272222 36273333
...
“我没有定义列的字段”这是第一步 - 使用ROWNUM创建一个查询,标识每个“cpf”组中的行号。然后pivoting将会更容易 –
我更喜欢交叉表到本地数据透视表。我觉得这个语法不那么呆板,性能通常会好一点。这是一篇关于交叉表的好文章。 http://www.sqlservercentral.com/articles/T-SQL/63681/如果您需要使此动态,您可以使用动态交叉表。 http://www.sqlservercentral.com/articles/Crosstab/65048/ –