MySQL DISTINCT для GROUP_CONCAT () - PullRequest
158 голосов
/ 21 июня 2010

Я делаю SELECT GROUP_CONCAT(categories SEPARATOR ' ') FROM table. Пример данных ниже:

categories
----------
test1 test2 test3
test4
test1 test3
test1 test3

Тем не менее, я получаю test1 test2 test3 test4 test1 test3 назад, и я хотел бы вернуть test1 test2 test3 test4. Есть идеи?

Большое спасибо!

Ответы [ 7 ]

323 голосов
/ 21 июня 2010

GROUP_CONCAT имеет атрибут DISTINCT:

SELECT GROUP_CONCAT(DISTINCT categories ORDER BY categories ASC SEPARATOR ' ') FROM table
43 голосов
/ 21 июня 2010

Использование DISTINCT будет работать

SELECT GROUP_CONCAT(DISTINCT(categories) SEPARATOR ' ') FROM table

REf: - это

16 голосов
/ 11 сентября 2013

Другие ответы на этот вопрос не возвращают то, что нужно OP, они возвращают строку вроде:

test1 test2 test3 test1 test3 test4

(обратите внимание, что test1 и test3 дублированы), в то время как OP хочет вернуть эту строку:

test1 test2 test3 test4

проблема здесь в том, что строка "test1 test3" дублируется и вставляется только один раз, но все остальные отличаются друг от друга ("test1 test2 test3" отличается от "test1 test3", даже если некоторые тесты содержатся в целом строка продублирована).

Здесь нам нужно разбить каждую строку на разные строки, и сначала нам нужно создать таблицу чисел:

CREATE TABLE numbers (n INT);
INSERT INTO numbers VALUES
(1),(2),(3),(4),(5),(6),(7),(8),(9),(10);

тогда мы можем выполнить этот запрос:

SELECT
  SUBSTRING_INDEX(
    SUBSTRING_INDEX(tableName.categories, ' ', numbers.n),
    ' ',
    -1) category
FROM
  numbers INNER JOIN tableName
  ON
    LENGTH(tableName.categories)>=
    LENGTH(REPLACE(tableName.categories, ' ', ''))+numbers.n-1;

и мы получаем такой результат:

test1
test4
test1
test1
test2
test3
test3
test3

и затем мы можем применить агрегатную функцию GROUP_CONCAT, используя предложение DISTINCT:

SELECT
  GROUP_CONCAT(DISTINCT category ORDER BY category SEPARATOR ' ')
FROM (
  SELECT
    SUBSTRING_INDEX(SUBSTRING_INDEX(tableName.categories, ' ', numbers.n), ' ', -1) category
  FROM
    numbers INNER JOIN tableName
    ON LENGTH(tableName.categories)>=LENGTH(REPLACE(tableName.categories, ' ', ''))+numbers.n-1
  ) s;

Пожалуйста, смотрите скрипку здесь .

10 голосов
/ 03 февраля 2017
SELECT
  GROUP_CONCAT(DISTINCT (category))
FROM (
  SELECT
    SUBSTRING_INDEX(SUBSTRING_INDEX(tableName.categories, ' ', numbers.n), ' ', -1) category
  FROM
    numbers INNER JOIN tableName
    ON LENGTH(tableName.categories)>=LENGTH(REPLACE(tableName.categories, ' ', ''))+numbers.n-1
  ) s;   

Это вернет различные значения, такие как: test1, test2, test4, test3

7 голосов
/ 02 апреля 2019

DISTINCT: даст вам уникальные значения.

SELECT GROUP_CONCAT(DISTINCT(categories )) AS categories FROM table
2 голосов
/ 01 апреля 2019

Вы можете просто добавить DISTINCT впереди.

SELECT GROUP_CONCAT(DISTINCT categories SEPARATOR ' ')

если вы хотите отсортировать,

SELECT GROUP_CONCAT(DISTINCT categories ORDER BY categories ASC SEPARATOR ' ')
1 голос
/ 29 июня 2017

Я понимаю, что этот вопрос старый, но я чувствую, что это должно быть упомянуто: group_concat с Different = Performance Killer. Если вы работаете с небольшими базами данных, вы этого не заметите, но при масштабировании - не очень хорошо.

...