Группировка SQL по словам LIKE (с подстановочными знаками), как добиться правильной суммы

Я работаю с запросом доступа в Excel VBA. Моя таблица содержит смесь более общих и специализированных продуктов, столбец со строками, например:

    Mountain bike x2321, 10
    Enduro Mountain bike special y3233, 20 
    Mountain bike a2a321, 10
    Skateboard z23233, 10
    Skateboard y2dsf3, 10
    Skadeboard pro advanced special 20, etc

Я хотел бы суммировать значения продаж, и я хотел бы агрегировать суммы по категориям, указанным в отдельной таблице B, словаре с подстроками: (

Специально для горных велосипедов, Скейтборд для горных велосипедов про скейтборд.

Я отсортировал таблицу в порядке убывания, чтобы более длинные имена отображались перед более короткими. При сортировке ожидается, что JOIN приведет к тому, что Scateboard pro будет проверен на существование против любой записи до того, как Scateboard будет протестирован.

Мой ожидаемый результат будет

Mountain bike special   Total 20
Mountain bike           Total  20
Skateboard pro Total  20
Skateboard      Total 20

Однако мой запрос включает все горные велосипеды, даже специальные, и все скейтборды, даже профессиональные, что неверно. Я бы хотел, чтобы они были объединены в отдельные категории. Сортировка по убыванию моего TableB, мой словарь не помог. :

Mountain bike special   Total 20
Mountain bike                 Total  40
Skateboard pro Total  20
Skateboard      Total 40

Мой предпринятый запрос включает поиск с LIKE и подстановочными знаками, он выглядит следующим образом:

SELECT "" Как kod, sum(b) Как wartosc, TableB.Descr как opis_grupy

FROM TableA LEFT JOIN TableB ON TableA.Descr LIKE (""+TableB.Descr+"")

ГДЕ TableA.a НЕ NULL

СГРУППИРОВАТЬ ПО TableB.Descr

ORDER BY TableB.Descr DESC

К сожалению, такой запрос не суммирует правильно. Я обдумывал использование FIRST np. http://www.mrexcel.com/forum/excel-questions/417807-sql-join-question-excel-access-only-return-first-join-instance.html (сначала функция восстановления), но Я понятия не имею, как это реализовать, чтобы запрос суммировался так, как ожидалось. Спасибо, что выручили меня.


person Jacek Kotowski    schedule 29.04.2015    source источник
comment
Обратите внимание, что order by никак не влияет на результат join.   -  person JimmyB    schedule 29.04.2015


Ответы (2)


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

SELECT TableA.descr AS aDescr, TableB.descr AS bDescr
FROM TableA
LEFT JOIN TableB on TableA.descr LIKE "*" + TableB.descr + "*"
GROUP BY TableA.descr, TableB.descr
HAVING len( TableB.descr ) = max( len( TableB.descr ) )

Обратите внимание на предложение HAVING, чтобы ограничить результаты самым длинным совпадением из TableB. Когда у вас есть этот набор данных, вы можете легко агрегировать его с помощью bDescr на следующем шаге.

person JimmyB    schedule 29.04.2015
comment
MS Access не понимает подстановочный знак %. оно использует * - person Krish; 29.04.2015
comment
Хорошо, что у нас есть стандарты в эти дни. - Спасибо за подсказку! - person JimmyB; 29.04.2015
comment
Спасибо Ханно. Я понял разницу в подстановочных знаках и попытался применить ее к своим данным. - person Jacek Kotowski; 29.04.2015

Спасибо, Ханно.

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

Мои данные:

ID  a   Descr   b
144 bbdd    VICRYL PLUS bbb 20
142 aacc    VICRYL PLUS aaa 20
10  dd22    VICRYL PLUS AAA     20
143 ggdc    VICRYL bbb  10
11  ss3d    VICRYL  10

Пробовал sql:

SELECT TableA.descr AS aDescr, TableB.descr AS bDescr
FROM TableA
LEFT JOIN TableB on TableA.descr LIKE ("*"+TableB.Descr+"*") 
GROUP BY TableA.Descr, TableB.Descr
HAVING len( TableB.Descr ) = max( len( TableB.Descr ) );

Соответствие, которое я получал, по-прежнему было неверным: aDescr bDescr

ВИКРИЛ ВИКРИЛ

ВИКРИЛ bbb ВИКРИЛ

ВИКРИЛ ПЛЮС ААА ВИКРИЛ

ВИКРИЛ ПЛЮС AAA ВИКРИЛ ПЛЮС

ВИКРИЛ ПЛЮС bbb ВИКРИЛ

ВИКРИЛ ПЛЮС bbb ВИКРИЛ ПЛЮС

РЕДАКТИРОВАТЬ: по предложению Ханно я попытался удалить TableB.descr из GROUP BYy. Я признаю, что делал пробы и ошибки без полного понимания. Это работало, только если я переместил max(TableB.Descr) в Select, чтобы избавиться от сообщения о том, что TableB.Descr должен быть в GROUP BY.

Поскольку в конечном итоге я хотел суммировать сгруппированные TableB.Descr, то, наконец, кажется, что это работает:

SELECT major, sum(b) FROM
  (SELECT  TableA.descr as opis, max(TableB.Descr) AS major, b
   FROM TableB 
   RIGHT JOIN TableA 
   ON  TableA.Descr LIKE ("*"+TableB.Descr+"*") 
   GROUP BY  TableA.descr,b )
GROUP BY major

Я еще не отмечаю как ответ. Ханно заслуживает большей похвалы, и мне нужно проверить его еще раз.

person Jacek Kotowski    schedule 29.04.2015
comment
Это должно было быть редактированием вашего вопроса. Если вы решили свою проблему, вы можете опубликовать ее как ответ, но для получения дополнительной информации/других вопросов она должна быть в самом вопросе. - person Clockwork-Muse; 29.04.2015
comment
Извините моя ошибка. Попробуйте только с GROUP BY TableA.Descr. - person JimmyB; 29.04.2015