Не чувствительные к регистру дубликаты SQL - PullRequest
11 голосов
/ 23 апреля 2010

Итак, у меня есть таблица пользователей, где user.username имеет много дубликатов, таких как:

username и Username и useRnAme
john и John и jOhn

Это была ошибка, и эти три записи должны были быть только одной.

Я пытаюсь найти SQL-запрос, в котором перечислены все эти случаи, упорядоченные по дате их создания, поэтомув идеале результат должен выглядеть примерно так:

username jan01
useRnAme jan02
Username jan03
john     feb01 
John     feb02
jOhn     feb03

Любые предложения будут высоко оценены

Ответы [ 5 ]

27 голосов
/ 23 апреля 2010

Оставляя в стороне вопрос чувствительности к регистру, базовая стратегия:

 SELECT username, create_date FROM your_table
     WHERE username IN 
     (SELECT username FROM your_table GROUP BY username HAVING COUNT(*) > 1)
 ORDER BY username, create_date

Многие РСУБД (включая MySQL, если предполагается, что вы используете CHAR или VARCHAR для столбца имени пользователя), выполняют поиск без учета регистра по умолчанию. Для этих баз данных вышеприведенное решение будет работать. Чтобы решить проблему чувствительности к регистру для других продуктов, включите все, кроме первого вхождения имени пользователя, в функцию преобразования в верхний регистр, специфичную для вашей СУБД:

 SELECT username, create_date FROM your_table
     WHERE UPPER(username) IN 
     (SELECT UPPER(username) FROM your_table GROUP BY UPPER(username) HAVING COUNT(*) > 1)
 ORDER BY username, create_date
1 голос
/ 23 апреля 2010

Попробуйте что-то вроде этого

SELECT UserName, CreatedDate
FROM User
WHERE LOWER(TRIM(UserName)) IN 
(
SELECT LOWER(TRIM(UserName))
FROM User
GROUP BY LOWER(TRIM(UserName))
HAVING count(*) > 1
)
0 голосов
/ 23 мая 2017
SELECT UserName, CreatedDate
FROM YourTable 
WHERE UserName COLLATE UTF8_BIN != LOWER(UserName COLLATE UTF8_BIN)
GROUP BY UserName, CreatedDate
HAVING COUNT(*) > 1
0 голосов
/ 23 апреля 2010

В MySQL сравнение с учетом регистра выполняется с использованием двоичного сопоставления. Таким образом, вы можете объединить таблицу самостоятельно и искать строки, в которых сравнение с учетом регистра отличается от сравнения без учета регистра:

select *
from YourTable t1
inner join YourTable t2 
on t1.name <> t2.name collate latin1_bin
and t1.name = t2.name
0 голосов
/ 23 апреля 2010

Используйте ToLower () или эквивалентную функцию в вашем SELECT и упорядочите по этому столбцу.

...