Исключая кортежи на основе максимального условия - PullRequest
2 голосов
/ 24 мая 2019

Я пытался ответить, чтобы решить эту проблему с SQL-запросом, но безуспешно.Проблема заключается в следующем:

ПРОБЛЕМА:

С учетом 4 таблиц, ИЗДЕЛИЯ , РЕМОНТ , ВЛАДЕЛЬЦЫ и НЕИСПРАВНОСТЬ , для каждого продукта Марка и модель отображают тип неисправности, которая устранялась чаще.

В таблицах есть следующие поля:

PRODUCTS: *Series_num, Brand, Model, Year, Code_Owner
OWNERS: *Code_Owner, Name, Surname, Street, Civic, City, (u)Phone
MALFUNCTIONS: *Malf_code, Desc
REPAIRS: *Series_num, *Malf_code, *Repair_Date, Price

* <- Primary key
(u) <- Unique attribute

Ожидаемый результат, учитывая этот пример данных:

| MODEL  |  BRAND   |  MALF_CODE  | NUMBER OF REPAIRS|
|----------------------------------------------------|
|   1    |  BRAND1  |      1      |        20        |
|   1    |  BRAND1  |      2      |        10        |
|   2    |  BRAND1  |      1      |         1        |
|   2    |  BRAND1  |      2      |         1        |
|   1    |  BRAND2  |      1      |        10        |
|   1    |  BRAND2  |      2      |        11        |

Должно быть:

| MODEL  |  BRAND   |  MALF_CODE  | NUMBER OF REPAIRS|
|----------------------------------------------------|
|   1    |  BRAND1  |      1      |        20        |
|   2    |  BRAND1  |      1      |         1        |
|   1    |  BRAND2  |      2      |        11        |

Обратите внимание, что BRAND1, MODEL: 2 имеетодинаковое количество ремонтов для двух разных типов неисправностей, поэтому один из рядов можно игнорировать или показать оба (неважно)


ЧТО I'VE TRIED:

Чтобы получить первую таблицу, я использовал простой запрос JOIN:

SELECT A.MODEL, A.BRAND, R.MALF_CODE, COUNT(*) AS N_REP
FROM REPAIRS R LEFT JOIN PRODUCTS A ON A.SERIES_NUM = R.SERIES_NUM
GROUP BY A.MODEL, A.BRAND, R.MALF_CODE;

Затем я попытался получить вторую таблицу благодаря MAX () function:

SELECT A.MODEL, A.BRAND, R.MALF_CODE, COUNT(*) AS N_REP
FROM REPAIRS R LEFT JOIN PRODUCTS A ON A.SERIES_NUM = R.SERIES_NUM
GROUP BY A.MODEL, A.BRAND, R.MALF_CODE
HAVING COUNT(*) IN(
    SELECT MAX(R.MALF_CODE)
    FROM REPAIRS R LEFT JOIN PRODUCTS A ON A.SERIES_NUM = R.SERIES_NUM
    GROUP BY A.MODEL, A.BRAND, R.MALF_CODE
    ORDER BY A.BRAND, R.MALF_CODE);

Но это вызывает у меня следующую ошибку:

[42000][907] ORA-00907: Missing closing Parenthesis

Кажется, я не могу найти ошибку.Я надеюсь, что я достаточно ясно.Заранее спасибо.

РЕДАКТИРОВАТЬ: я забыл упомянуть, что я знаю о функциях RANK и тому подобное, но никогда не слышал о разделах.Поэтому решение без них высоко ценится, но не обязательно.

1 Ответ

2 голосов
/ 24 мая 2019

Если я правильно понимаю, вам нужен ряд с наибольшим количеством ремонтов для каждой комбинации модель / марка. Если это так, оконные функции являются одним из методов:

SELECT MODEL, BRAND, MALF_CODE, N_REP
FROM (SELECT P.MODEL, P.BRAND, R.MALF_CODE, COUNT(*) AS N_REP,
             ROW_NUMBER() OVER (PARTITION BY P.MODEL, P.BRAND ORDER BY COUNT(*) DESC, R.MALF_CODE) as SEQNUM
      FROM REPAIRS R LEFT JOIN
           PRODUCTS P
           ON P.SERIES_NUM = R.SERIES_NUM
      GROUP BY P.MODEL, P.BRAND, R.MALF_CODE
     ) MB
WHERE seqnum = 1;
...