sql - 包含多条记录的数据

时间:2016-07-26 13:56:00

标签: sql sql-server tsql

我有以下临时表

enter image description here

目标是使用多个记录标记数据并放入More than one records

在下面的示例中,如果Siren出现多次,我会

Siren           ETS_RS                                 Voie                      Ville              nom_etp
348177155       POITOU-CHARENTES ENGRAIS  P.C.E. (SNC) BOULEVARD WLADIMIR MORCH  17000 LA ROCHELLE  More than one records

对于出现一次的记录,我将拥有该公司的单一名称(此处为nom_etp

Siren           ETS_RS                                 Voie                      Ville              nom_etp
344843347       PRESTIGE AUTO ROCHELAIS (SAS)          4  RUE JEAN DEMEOCQ       17000 LA ROCHELLE  NIGER

我尝试了一些基于这样的想法:如果我可以计算多个,我可以轻松标记它们并使用CASE

首先:我试着做一次计数

WITH cte_ssrep_moraux AS (...)
SELECT SIREN,ETS_RS,Voie,Ville
,Denomination AS nom_etp,COUNT(SIREN)
FROM cte_ssrep_moraux
GROUP BY ETS_RS,Voie,Ville,Denomination,SIREN

当所有计数等于1时,它会出现一个小故障,并且我拥有与图片中相同的数据集...

第二

WITH cte_ssrep_moraux AS (...)
SELECT ETS_RS,Voie,Ville
,Denomination AS nom_etp,SIREN,
RANK() OVER (PARTITION BY ETS_RS ORDER BY ETS_RS ASC) AS  xx
FROM cte_ssrep_moraux
GROUP BY ETS_RS,Voie,Ville,Denomination,SIREN

当所有计数等于1时,它会出现一个小故障,并且我拥有与图片中相同的数据集...

我对下一步该做什么感到困惑。我有一种轻松的感觉,我将面对自己。

非常感谢您阅读我的问题

6 个答案:

答案 0 :(得分:2)

如果这是您的标准:

  

如果Siren出现不止一次,

然后group by子句应该只包含Siren

SELECT SIREN, COUNT(*)
FROM cte_ssrep_moraux
GROUP BY SIREN
HAVING COUNT(*) > 1;

我不确定您之后要做什么,但这会返回多次出现的SIREN值。

答案 1 :(得分:2)

如果有多行并且您将每个nom_etp更改为“多个记录”,则最终会得到相同的行。这就是我准备一些调整查询的原因。请参阅以下内容(为清晰起见,表格已简化):

CREATE TABLE Duplicates
(
    Id int,
    Name varchar(20),
    Item varchar(20)
)
INSERT Duplicates VALUES
(1,'Name1', 'Item1'),
(2,'Name2', 'Item2'),
(2,'Name2', 'Item3'),
(3,'Name3', 'Item4'),
(3,'Name3', 'Item5'),
(3,'Name3', 'Item6'),
(4,'Name4', 'Item7');

如果您只需要一个查询:

WITH Numbered AS
(
    SELECT Id, Name, Item,
        ROW_NUMBER() OVER (PARTITION BY Id ORDER BY Id) RowNum,
        COUNT(*) OVER (PARTITION BY Id ORDER BY ID) TotalInGroup
    FROM Duplicates
)
SELECT Id, Name,
    CASE WHEN RowNum=1 AND TotalInGroup>1 THEN 'More records' ELSE Item END Item
FROM Numbered

如果您需要规范化:

WITH Numbered AS
(
    SELECT Id, Name, Item,
        ROW_NUMBER() OVER (ORDER BY Id) Number,
        ROW_NUMBER() OVER (PARTITION BY Id ORDER BY Id) RowNum,
        COUNT(*) OVER (PARTITION BY Id ORDER BY ID) TotalInGroup
    FROM Duplicates
)
MERGE Numbered AS tgt
USING Numbered AS src
ON src.Number=tgt.Number
WHEN MATCHED AND tgt.RowNum=1 AND tgt.TotalInGroup>1 THEN
    UPDATE SET tgt.Item='More'
WHEN MATCHED AND tgt.RowNum>1 THEN
    DELETE;

表格如下所示:

Id  Name    Item
--  ----    ----
1   Name1   Item1
2   Name2   More
3   Name3   More
4   Name4   Item7

如果有多个行具有相同的ID,则首先使用“更多”常量更新这些行,并删除该组中的所有其他行。

答案 2 :(得分:1)

为此目的使用CTE

;WITH CTE AS(
SELECT ETS_RS,Voie,Ville,Denomination AS nom_etp,SIREN,
    ROW_NUMBER() OVER (PARTITION BY ETS_RS ORDER BY ETS_RS ASC) AS  RN
FROM cte_ssrep_moraux
--GROUP BY ETS_RS,Voie,Ville,Denomination,SIREN
)
SELECT ETS_RS,
   Voie,Ville,
   CASE WHEN RN > 1 THEN 'More than one records'
        ELSE nom_etp
        END AS 'nom_etp',
        SIREN
FROM CTE

答案 3 :(得分:1)

;with cte
as
(
select siren,count(*) as cnt
from
yourtable
having count(*)>1
)
update t
set nom_etp='more than one records'
yourtable t where exists(Select 1 from cte c where c.sirenid=t.sirenid)

答案 4 :(得分:1)

因为您仍然需要所有记录,包括唯一的记录。

然后你可以使用COUNT作为窗口功能 使用CASE选择显示为nom_etp的内容。

select Siren, ETS_RS, Voie, Ville,
(case when count(*) over (partition by Siren) > 1 then 'More than one records' else nom_etp end) as nom_etp
from cte_ssrep_moraux;

答案 5 :(得分:1)

请找我做的

WITH cte_ssrep_moraux AS (
SELECT SIREN,ETS_RS,Voie,Ville
,Denomination AS nom_etp,ROW_NUMBER() 
OVER (PARTITION BY ETS_RS ORDER BY ETS_RS ASC) AS  Counting
FROM 
(my_initial_cte) AS tb
)
SELECT Siren, ETS_RS, Voie, Ville,nom_etp
FROM cte_ssrep_moraux
WHERE counting = 1
AND Siren NOT IN  (SELECT Siren FROM cte_ssrep_moraux WHERE counting > 1)
UNION ALL 
SELECT DISTINCT Siren, ETS_RS, Voie, Ville,'More than one records'
FROM cte_ssrep_moraux
WHERE counting > 1   

说明:在最初的CTE之后,我尝试了上面提到的许多解决方案,特别是使用CASE

CASE的问题在于它会提供类似的内容

 Siren ETS_RS Voie  Ville     nom_etp
 xxxx  xyxy   xyzet Bordeaux  More than one records
 xxxx  xyxy   xyzet Bordeaux  More than one records
 xxxx  xyxy   xyzet Bordeaux  More than one records
 xxxy  zzzy   ssare Paris     Firm ABC

所以不要把所有东西放在CASE之下,我说让我们把它分成两部分:

  1. 第一部分会将所有计数等于1
  2. 第二部分将使用DISTINCT
  3. 计算超过1的计数
  4. 使用UNION ALL加入两个结果,因为这两组具有相同数量的提取行