MySQL — Выберите значение только один раз на основе другого поля

#mysql #sql

#mysql #sql

Вопрос:

Моя схема базы данных выглядит следующим образом:

 CREATE TABLE test (
  id INT(11) UNSIGNED PRIMARY KEY,
  title VARCHAR(255) NOT NULL,
  priority ENUM('low', 'medium', 'high') NOT NULL
);

INSERT INTO test (id, title, priority) VALUES (1, 'test', 'medium');
INSERT INTO test (id, title, priority) VALUES (2, 'test', 'high');
INSERT INTO test (id, title, priority) VALUES (3, 'test2', 'low');
  

И мой запрос выглядит следующим образом:

 SELECT * FROM test 
ORDER BY FIELD(priority, 'high', 'medium', 'low');
  

Я хотел бы сделать DISTINCT поле on title на основе priority поля. Например, если есть два или более одинаковых данных title , я хотел бы выбрать только те, которые имеют наивысший приоритет, поэтому в моем случае ожидаемыми результатами будут данные с идентификаторами 2 и 3. Как это сделать?

Ответ №1:

Один из методов:

 SELECT t.*
FROM test t
WHERE FIELD(priority, 'high', 'medium', 'low') =
          (SELECT MIN(FIELD(priority, 'high', 'medium', 'low'))
           FROM test t2
           WHERE t2.title = t.title
          );
  

Редактировать:

Я не думал, что приоритеты могут повторяться. Вышеуказанное можно изменить, чтобы использовать id :

 SELECT t.*
FROM test t
WHERE id = (SELECT id
            FROM test t2
            WHERE t2.title = t.title
            ORDER BY FIELD(priority, 'high', 'medium', 'low')
            LIMIT 1
           );
  

Комментарии:

1. Спасибо, но есть проблема. Например, если два данных имеют одинаковый заголовок и приоритет, они оба выбраны. Вместо этого я бы ожидал выбрать только одно из двух.

2. @Bob, попробуй добавить Group by t.title, t.priority в конец этого запроса.

3. @Bob . . . Это решается с помощью id в подзапросе, а не приоритета. На самом деле это немного упрощает запрос.

Ответ №2:

Попробуйте это…

Таблица и образцы данных

 CREATE TABLE test (
  id INT(11) UNSIGNED PRIMARY KEY,
  title VARCHAR(255) NOT NULL,
  priority ENUM('low', 'medium', 'high') NOT NULL
);

INSERT INTO test (id, title, priority) VALUES (1, 'test', 'medium');
INSERT INTO test (id, title, priority) VALUES (2, 'test', 'high');
INSERT INTO test (id, title, priority) VALUES (3, 'test2', 'low');
INSERT INTO test (id, title, priority) VALUES (4, 'test2', 'low');
INSERT INTO test (id, title, priority) VALUES (5, 'test2', 'low');
INSERT INTO test (id, title, priority) VALUES (6, 'test', 'low');
INSERT INTO test (id, title, priority) VALUES (7, 'test3', 'low');
INSERT INTO test (id, title, priority) VALUES (8, 'test3', 'high');
INSERT INTO test (id, title, priority) VALUES (9, 'test3', 'medium');
  

Запрос

 SELECT Max(t2.id)  AS ID,
       t1.title    AS Title,
       t1.priority AS Priority
FROM   (SELECT title,
               Min(priority) AS priority
        FROM   test
        GROUP  BY title
        ORDER  BY Field(priority, 'high', 'medium', 'low')) t1
       INNER JOIN test t2 using (title, priority)
GROUP  BY t1.title,
          t1.priority;  
  

Вывод

  ----- -------- ---------- 
| ID  | Title  | Priority |
 ----- -------- ---------- 
|  2  | test   | high     |
|  5  | test2  | low      |
|  8  | test3  | high     |
 ----- -------- ----------