1 / 1 / 1
Регистрация: 07.12.2016
Сообщений: 34
1

Запрос LEFT JOIN с применением статистических выражений

17.08.2017, 18:50. Показов 1233. Ответов 10
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
Добрый день!

В рамках одной БД имеется две таблицы (проверки и ошибки).

TableA (TableA.ID, TableA.Datechecks, TableA.CheckedFIO, TableA.CheckTypes)
TableB (TableB.ID, TableB.IDA, TableB.Mistake, TableB.MistakeCriticality)

Необходимо подготовить запрос, который бы отображал следующие данные:
ФИО, Кол-во проверок, Общее кол-во ошибок, Кол-во ошибок_Ошибка, Кол-во ошибок_Гр.ошибка, Кол-во проверок без ошибок, кол-во проверок без грубых ошибок.

Подобный запрос смог реализовать только без группировки по ФИО, вот что получилось (уверен, что можно было бы еще проще написать):
SQL
1
2
3
4
5
6
7
8
9
10
11
12
13
14
SELECT (SELECT COUNT(*)
 FROM (SELECT DISTINCT TableA.ID FROM TableA LEFT JOIN TableB ON TableA.ID = TableB.IDA)) AS Проверки,
 COUNT(TableB.ID) AS Ошибки,
 SUM(IIf(TableB.MistakeCriticality='Грубая ошибка',1,0)) AS Ошибки_ГРУБАЯ,
 SUM(IIf(TableB.MistakeCriticality='Ошибка',1,0)) AS Ошибки_ОШИБКА,
 (SELECT COUNT(*) FROM (SELECT DISTINCT TableA.ID
                                     FROM TableA
                                     LEFT JOIN TableB
                                     ON TableA.ID = TableB.IDA WHERE TableB.IDA IS NULL)) AS Проверки_без_ошибок,
  (Проверки-(SELECT COUNT(*)  FROM (SELECT DISTINCT TableA.ID
                                                           FROM TableA
                                                           LEFT JOIN TableB ON TableA.ID = TableB.IDA
                                                           WHERE TableB.MistakeCriticality = 'Грубая ошибка'))) AS Проверки_без_Грубых_ошибок
 FROM TableA LEFT JOIN TableB ON TableA.ID = TableB.IDA
При попытке добавить группировку по ФИО, т.е. добавляю поле TableA.CheckedFIO и в конце пишу GROUP BY TableA.CheckedFIO, выдает актуальные данные только по "Ошибки", "Ошибки_ГРУБАЯ", "Ошибки_ОШИБКА", все остальные данные имеют одинаковое значение, т.е. сумму, без разбивки по конкретным ФИО.

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

Заранее спасибо!
0
Лучшие ответы (1)
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
17.08.2017, 18:50
Ответы с готовыми решениями:

LEFT JOIN и вложенный запрос
Задание по БД...Прикрепляю ниже БД. Необходимо сделать такой запрос: Написать процедуру,...

LEFT JOIN и отдельный запрос
Такой запрос работает SELECT tblСЭТ.fldIdСЭТ, tblСЭТ.fldТочкаУчета, tblСЭТ.fldТипСЭТ, ...

Запрос left join с группировкой по 2 полям
Здравствуйте. Есть таблица дата - продукция - масса - движение (приход или расход) Нужно...

Переделать запрос LEFT JOIN -> INNER JOIN
Доброго времени суток, помогите переделать запрос с использованием LEFT JOIN на INNER JOIN ...

10
Эксперт MS Access
2833 / 1375 / 215
Регистрация: 13.05.2011
Сообщений: 4,217
17.08.2017, 19:22 2
diadlos, а пример базы можете выложить? Чтобы уж наверняка.
0
1 / 1 / 1
Регистрация: 07.12.2016
Сообщений: 34
18.08.2017, 10:48  [ТС] 3
Вячеслав Я, вот тестовая БД.
Вложения
Тип файла: zip test_bd.zip (70.6 Кб, 4 просмотров)
0
Модератор
Эксперт MS Access
11956 / 4824 / 779
Регистрация: 07.08.2010
Сообщений: 14,128
Записей в блоге: 4
18.08.2017, 11:39 4
Цитата Сообщение от diadlos Посмотреть сообщение
Подобный запрос смог реализовать только без группировки по ФИО, вот что получилось (уверен, что можно было бы еще проще написать):
сколько же в запросе уровней вложения под-запросов
не смогла сосчитать
Ох, нелегкая это работа -
Из болота тащить бегемота!
0
1 / 1 / 1
Регистрация: 07.12.2016
Сообщений: 34
18.08.2017, 11:50  [ТС] 5
shanemac51, все из-за того, что требуются кол-во уникальных значений, а как я понял в Access вывести кол-во уникальных можно только select count(*) from (select distinct .......).
Ну и как я говорил, можно конечно было сделать его попроще, я так думаю (просто я пока не знаю как ).
0
Эксперт MS Access
26805 / 14484 / 3192
Регистрация: 28.04.2012
Сообщений: 15,782
18.08.2017, 12:08 6
diadlos, попробуйте запрос
SQL
1
2
3
4
5
transform COUNT(*)
SELECT Checks.CheckedFIO, COUNT(*) AS Проверки, Проверки+SUM(Mistake_Criticality="Грубая ошибка") AS БезГрубыхОшибок
FROM Checks INNER JOIN CheckMistakes ON Checks.ID = CheckMistakes.ID_Check
GROUP BY Checks.CheckedFIO
pivot CheckMistakes.Mistake_Criticality
Добавлено через 4 минуты
Если запрос выдает неверный набор, то нарисуйте табличку правильных данных и выложите здесь
1
1 / 1 / 1
Регистрация: 07.12.2016
Сообщений: 34
18.08.2017, 13:05  [ТС] 7
mobile, попробовал запрос, но он сразу выдал некорректные значения по полю "Проверки", т.е. он подсчитал кол-во ID с группировкой по ФИО, а нужно кол-во уникальных ID с группировкой по ФИО. У нас же получается, что LEFT JOIN выводит все проверки и ошибки, при этом часть таблицы по проверкам дублируется, если в одной проверке была найдена не одна ошибка, а две и более.

Ниже скрин таблицы с корректными данными, которые должны быть (высчитал вручную ).

ФИО сотрудникаВсего проверокВсего ошибокОшибки _ГРУБАЯОшибки _ОШИБКАПроверки без ошибокПроверки без грубых ошибок
Иванов Иван Иванович542233
Королев Антон Сергеевич131200
Петров Петр Петрович7105544
Федоров Федр Федорович751446
Миниатюры
Запрос LEFT JOIN с применением статистических выражений  
0
Эксперт MS Access
26805 / 14484 / 3192
Регистрация: 28.04.2012
Сообщений: 15,782
18.08.2017, 14:26 8
Лучший ответ Сообщение было отмечено diadlos как решение

Решение

diadlos, попробуйте вариант
SQL
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
SELECT CheckedFIO, SUM(vsego) AS ВсегоПроверок, SUM(c) AS ВсегоЗаписей,
SUM(vsego_err) AS ВсегоОшибок,
SUM(err_hard) AS ОшибкиГрубые,
SUM(err_err) AS ОшибкиОшибка,
ВсегоЗаписей-ОшибкиГрубые-ОшибкиОшибка AS ПроверкиБезОшибок,
SUM(not_err_hard) AS ПроверкиБезГрубыхОшибок
FROM
(SELECT Checks.ID, Checks.CheckedFIO, 1 AS vsego,  COUNT(*) AS c,
-SUM(CheckMistakes.Mistake_Criticality IS NOT NULL) AS vsego_err, 
-SUM(Mistake_Criticality="Грубая ошибка") AS err_hard, 
-SUM(Mistake_Criticality="ошибка") AS err_err,
-SUM(CheckMistakes.Mistake_Criticality IS NULL) AS notErr,
iif(err_hard>0,0,1) AS not_err_hard
FROM Checks LEFT JOIN CheckMistakes ON Checks.ID = CheckMistakes.ID_Check
GROUP BY Checks.ID, Checks.CheckedFIO) t
GROUP BY t.CheckedFIO
1
1 / 1 / 1
Регистрация: 07.12.2016
Сообщений: 34
18.08.2017, 15:22  [ТС] 9
mobile, он сработал! Огромное спасибо за помощь!!!
Однако у меня возникли вопросы, при разборе этого запроса, не мог бы ты немного пояснить:

1. Почему в команде "SUM(CheckMistakes.Mistake_Criticality IS NOT NULL)" мы используем "-", т.е. почему без "-" выводится отрицательное значение? Да и в других командах, где используем "-".

2. В команде "COUNT(*) AS c" количество чего именно мы считаем? Судя по таблице мы считаем кол-во err_hard, err_err, notErr, not_err_hard. Если это так, то почему у нас там не учитывается vsego_err? Ведь COUNT(*) идет перед все этой комбинацией.

Сори, если вопросы глупые ...
0
Эксперт MS Access
26805 / 14484 / 3192
Регистрация: 28.04.2012
Сообщений: 15,782
18.08.2017, 18:11 10
Цитата Сообщение от diadlos Посмотреть сообщение
1. Почему в команде "SUM(CheckMistakes.Mistake_Criticality IS NOT NULL)" мы используем "-", т.е. почему без "-" выводится отрицательное значение? Да и в других командах, где используем "-".
Потому что суммируются логические выражения, которые могут быть только True или False. True в Access=-1, а False=0. Поскольку суммируем только True, то результат отрицательный и перед ним ставится минус.

Цитата Сообщение от diadlos Посмотреть сообщение
В команде "COUNT(*) AS c" количество чего именно мы считаем?
Считаем общее количество записей в группе по Проверяемому. Для Иванова всего 7 записей, у Петрова 14 и так далее. По Вашему ТЗ этот параметр как бы не нужен, но я добавил для наглядности.
1
1 / 1 / 1
Регистрация: 07.12.2016
Сообщений: 34
18.08.2017, 18:51  [ТС] 11
Цитата Сообщение от mobile Посмотреть сообщение
Считаем общее количество записей в группе по Проверяемому. Для Иванова всего 7 записей, у Петрова 14 и так далее. По Вашему ТЗ этот параметр как бы не нужен, но я добавил для наглядности.
Все, я понял. Потом мы просто минусуем от кол-ва строк те строки, где есть ошибки и грубые ошибки.

В общем еще раз спасибо за помощь!
0
18.08.2017, 18:51
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
18.08.2017, 18:51
Помогаю со студенческими работами здесь

Запрос по left join
Здравствуйте. Подскажите логику запроса. Имеется стандартный select A.name1, A.name2, count...

Запрос с Left Join
Ребят, помогите пожалуйста разобраться! Нужно запрос построить, вообще, в Access, но думаю не...

Запрос на выборку и LEFT JOIN
Здравствуйте! Есть такая задача: Нужно написать SQL запрос, который будет работать в MySQL...

Запрос к БД с использованием LEFT JOIN
Добрый день дорогие эксперты, профессионалы и любители. Помогите вкурить как сделать правильно,...

Как оптимизировать запрос с Left Join?
Есть такой запрос, выполняется очень долго (30 секунд), в базе в таблице news 85 тысяч записей, а в...

Запрос с LEFT JOIN
Добрый день. Либо я что-то делаю не так, либо не пойму как работает запрос с LEFT JOIN Вывожу...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
11
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru