SQL Server:根据两列

时间:2015-11-12 17:18:02

标签: sql sql-server

我正在努力清理电子商务网站上的客户列表。客户列表在客户ID和客户电子邮件之间存在多对多的关系。例如,客户可以在登录或匿名时使用相同的电子邮件下订单,结果将是具有相同电子邮件但具有不同客户ID的两个客户记录。类似地,客户可以在登录时创建具有两个不同电子邮件的订单,这将导致具有相同ID但不同电子邮件的客户记录。鉴于此,我想根据电子邮件或客户编号创建具有真正唯一ID的客户列表。此外,在某些情况下,电子邮件是空白的,因此客户记录两者都有空白电子邮件,但不同的ID需要被视为两个不同的客户。

所以给出这样的东西:

CUST_ID CUST_EMAIL
------------------------
123     test1@gmail.com
123     test2@gmail.com
124     test3@gmail.com
125     test3@gmail.com
126
127
128     test4@gmail.com
128     test5@gmail.com
129     test4@gmail.com

我想生成一个这样的键:

CUST_ID CUST_EMAIL      NEW_CUST_KEY
------------------------------------
123     test1@gmail.com     1
123     test2@gmail.com     1
124     test3@gmail.com     2
125     test3@gmail.com     2
126                         3
127                         4
128     test4@gmail.com     5
128     test5@gmail.com     5
129     test4@gmail.com     5

3 个答案:

答案 0 :(得分:1)

OLDTABLE - 是你的桌子 NEWTABLE - 将有结果

enter image description here

var N = 50

function asyncFunc (cb) {  
  setTimeout(() => cb(Math.random()), 100)
}

function loop (max, results, done) {  
  // Recursion base-case
  if (results.length >= max) return done(results)

  asyncFunc((res) => {
    results.push(res)
    loop(max, results, done)
  })
}

let randomNumbers = []  
loop(N, randomNumbers, function (results) {  
  console.log(results)
})

答案 1 :(得分:0)

我认为你可以使用row_number ..... 像这样......

SELECT DISTINCT CUST_ID, CUST_EMAIL
ROW_NUMBER() OVER(PARTITION BY CUST_ID, CUST_EMAIL) AS New_Cust_Key
FROM YOUR TABLES

答案 2 :(得分:0)

我试图将用户的ID映射到他们的电子邮件,反之亦然,因此我创建了这个Frankenstein怪物查询:

DECLARE @Customers TABLE
(
  CUST_ID INT
  , CUST_EMAIL VARCHAR(20)
);

INSERT INTO @Customers (CUST_ID, CUST_EMAIL)
VALUES (123, 'test1@gmail.com')
  , (123, 'test2@gmail.com')
  , (124, 'test3@gmail.com')
  , (125, 'test3@gmail.com')
  , (126, '')
  , (127, '')
  , (128, 'test4@gmail.com')
  , (128, 'test5@gmail.com')
  , (129, 'test4@gmail.com');


SELECT DISTINCT C.CUST_ID
  , C.CUST_EMAIL
  , DENSE_RANK() OVER(ORDER BY T.CUST_ID) AS NEW_CUST_KEY
FROM @Customers AS C
INNER JOIN (
  SELECT CUST_ID, CUST_EMAIL
  FROM @Customers
  EXCEPT
  SELECT C2.CUST_ID, C2.CUST_EMAIL
  FROM @Customers AS C1
  INNER JOIN @Customers AS C2
    ON C2.CUST_EMAIL = C1.CUST_EMAIL
    AND C2.CUST_ID > C1.CUST_ID
    AND C1.CUST_EMAIL <> ''
  ) AS T
  ON CASE
    WHEN (T.CUST_ID = C.CUST_ID AND T.CUST_EMAIL = C.CUST_EMAIL AND T.CUST_EMAIL = '') THEN 1
    WHEN (T.CUST_ID = C.CUST_ID OR T.CUST_EMAIL = C.CUST_EMAIL) AND T.CUST_EMAIL <> '' THEN 1
    ELSE 0
  END = 1;

使用您生成的测试数据,它确实符合您的期望:

╔═════════╦═════════════════╦═══════════════╗
║ CUST_ID ║   CUST_EMAIL    ║ NEW_CUST_KEY  ║
╠═════════╬═════════════════╬═══════════════╣
║     123 ║ test1@gmail.com ║             1 ║
║     123 ║ test2@gmail.com ║             1 ║
║     124 ║ test3@gmail.com ║             2 ║
║     125 ║ test3@gmail.com ║             2 ║
║     126 ║                 ║             3 ║
║     127 ║                 ║             4 ║
║     128 ║ test4@gmail.com ║             5 ║
║     128 ║ test5@gmail.com ║             5 ║
║     129 ║ test4@gmail.com ║             5 ║
╚═════════╩═════════════════╩═══════════════╝

您可以在data.stackexchange.com

的现实生活中看到这一点

请告诉我这是否适用于您的实际数据库。