MySQL - сохраняйте дубликаты и порядок в запросе WHERE IN - PullRequest
0 голосов
/ 25 октября 2018

У меня большой набор значений, например, из таблицы "table_name"

('12345','12345', '48373')

Этот список на самом деле намного больше.Около 20 тыс.

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

 **processid**     **desc**
 12345              name
 48373              name2

Я хочу, чтобы результат был в порядке и сохранял дубликаты.Когда я запрашиваю, как это:

SELECT processid, desc FROM table_name WHERE processid IN ('12345','12345', '48373');

Результат:

12345   name
48373   name2

Но я хочу:

12345   name
12345   name
48373   name2

Ответы [ 3 ]

0 голосов
/ 25 октября 2018

Обходной путь может быть программным, где вы можете сохранить многомерный массив с ключом и значениями, где ключ будет обработан, а значение будет счетчиком (сколько раз вы хотите отобразить идентификатор процесса). В итерации цикла результата запросаВы можете проверить processid с помощью ключа массива и отобразить его по значению массива.

Надеюсь, это поможет.

0 голосов
/ 25 октября 2018

Чтобы извлечь записи в порядке, указанном в предложении IN, вам необходимо переместить критерии IN в оператор подвыбора и использовать JOIN ON этого набора результатов в основной таблице.

Чтобы сделать его менее запутанным и немного более быстрым, используйте временную таблицу для хранения значений, которые вы хотите получить из основной таблицы.Используйте столбец с автоинкрементом для сохранения желаемого порядка записей.

Пример http://sqlfiddle.com/#!9/a4e6ab/2

CREATE TEMPORARY TABLE IF NOT EXISTS tmp_ids (
    id INT NOT NULL AUTO_INCREMENT PRIMARY KEY,
    processid INT
);

INSERT INTO tmp_ids (processid)
VALUES 
    (12345),
    (12345),
    (48373);

SELECT
    m.processid,
    m.`desc`
FROM tmp_ids AS tmp
INNER JOIN main_table AS m
ON tmp.processid = m.processid
ORDER BY tmp.id ASC;

#optional drop the temporary table
DROP TEMPORARY TABLE IF EXISTS tmp_ids;

Результат

| processid |  desc |
|-----------|-------|
|     12345 |  name |
|     12345 |  name |
|     48373 | name2 |

Почему WHERE IN не будет работать

Как уже упоминалось, MySQL не использует критерии WHERE для сохранения желаемого порядка и будет игнорировать дублирующиеся оценки, которые в нем содержатся.Это связано с тем, что критерий WHERE оценивается только как true или false, чтобы определить, какие записи из таблицы (таблиц) следует извлечь или на которые можно повлиять.Соответствие только строкам, указанным в условиях WHERE, которые оцениваются как true.

IN, в частности, может рассматриваться как сжатая форма повторяющихся OR условий для указанного столбца.

Значение вашего исходного запроса раскрывается как;Найти записи в table_name, которые имеют processid, равный 12345 ИЛИ 12345 ИЛИ 48373.

Например, используя следующие данные таблицы

table_name

| id |
|----|
|   1|
|   1|
|   2|
|   1|

Используя запрос типа

SELECT * 
FROM table_name
WHERE id IN(1, 3);

который расширяется как;найти записи, у которых id равно 1 ИЛИ 3.

В результате получается следующий набор записей

| id |
|----|
|   1|
|   1|
|   1|
0 голосов
/ 25 октября 2018

Простой ответ для вас: вы не можете получить эти результаты, основываясь на предложении where .

Теперь позвольте мне объяснить, почему.Предложение WHERE представляет собой набор условий для FILTER данных в вашей таблице, которые никоим образом не добавляют больше данных к существующим данным.если у вас есть 2 реестра в вашей таблице, и вы не можете добавить больше, чем это, к результату, запрашивающему его (если вы не используете что-то вроде Салман показал вам).

Так что если ваша таблицапросто

 12345   name
 48373   name2

Результаты будут основаны только на этих 2 строках.Предложение WHERE будет проверять только то, оценивается ли это условие как истинное или ложное, поэтому:

processid IN ('12345','12345', '48373') это будет проверять все значения в столбце processid, такие как эта строка за строкой (приблизительно объясняя):

  • Для строки (имя 12345) это значение процесса в предложении IN: ИСТИНА
  • Для строки (имя 48232) это значение процесса в предложении IN: ИСТИНА

Тогда у вас есть только две строки в качестве результатов.

Как я уже говорил, без использования какой-либо техники, которая фактически добавляет больше строк в ваш набор результатов (объединение всех, CTE иличто угодно) вы не можете получить желаемый результат, исходя из того, сколько раз вы добавляете условие в предложении WHERE.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...