Форум программистов, компьютерный форум, киберфорум
Delphi: Базы данных
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 5.00/3: Рейтинг темы: голосов - 3, средняя оценка - 5.00
0 / 0 / 0
Регистрация: 23.07.2013
Сообщений: 50
1

SQL-запрос работает наполовину. Нужен совет

24.10.2016, 11:12. Показов 628. Ответов 12
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
Здравствуйте! Проблема с SQL-запросом. В Delphi Сиэтл установил ADOConnection, ADOQuery и DBGrid. ADOConnection связан с базой Access 2003 формата через драйвер Jet 4.
Использую запрос, чтобы вытащить из базы данных заявок от пользователей те заявки, которые удовлетворяют следующим требованиям:

1) Дата создания заявки (DataSozd) находится между Dat1 и Dat2.

2)Дата создания заявки меньше, чем Dat1 и её состояние (Sostoyanie) = ‘Не выполнено’ + у заявки есть копии (ShhetchikKopij > 0)

3) Дата создания заявки меньше, чем Dat1, но её состояние уже равно ‘Выполнено’ и дата выполнения (DataVypoln) > Dat1 + у заявки тоже есть копии (ShhetchikKopij > 0)

Вот кусок кода:

Delphi
1
2
3
4
5
ADOQuery1.SQL.Add('Select * From Zayavki Where (((DataSozd>=:Dat1) And (DataSozd<=:Dat2)) Or (DataSozd<=:Dat1) And
((Sostoyanie=' + QuotedStr('Не выполнено') + ') Or ((Sostoyanie=' + QuotedStr('Выполнено') + ') And (DataVypoln Is Not Null) And (DataVypoln>=:Dat3))) And (ShhetchikKopij>0));');
ADOQuery1.Parameters.ParamByName('Dat1').Value := Data1;
ADOQuery1.Parameters.ParamByName('Dat2').Value := Data2;
ADOQuery1.Parameters.ParamByName('Dat3').Value := Data1;
Пояснения:

Zayavki – имя таблицы, содержащей заявки от пользователей на выполнение каких-то работ.
DataSozd – поле типа Дата/Время – Дата создания заявки
Sostoyanie – поле типа Текст – в нём могут храниться только 2 значения (я проверял, 3-го нет нигде): Выполнено или Не выполнено.
DataVypoln - поле типа Дата/Время – Дата выполнения заявки
ShhetchikKopij – поле типа Длинное целое – Счетчик количества копий данной заявки
Dat1, Dat2 и Dat3 – параметры типа Дата/Время, Data1 и Data2 - переменные типа TDateTime.

Запрос в таком виде НЕ выполняется, ошибок никаких НЕ выдает, просто пустой DBGrid и ADOQuery.RecordCount = 0. Если запрос разбить на 2 отдельных запроса: 1 запрос - условие, которое перед самым первым "Or", 2 запрос - всё остальное, то эти 2 запроса по отдельности прекрасно ВЫПОЛНЯЮТСЯ.

КАК слить их воедино и в чём причина? Спасибо.
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
24.10.2016, 11:12
Ответы с готовыми решениями:

Нужен совет по SQL
Народ возникла такая проблема. Решил подучить php. И возникла такая проблема при работе с базой...

Нужен совет по DBMS Sql
Начинаю с 0...не могу разобраться с заданием... Задание: создать блок PL/SQL, в котором создать...

Нужен совет в составлении Sql-запроса
Помогите составить Sql-запрос очень сильно нужно. Сайт на DLE. Есть поле short_story в нем вот...

Запрос суммыдт из проводок. Нужен совет
Нужно выбрать из проводки документа сумму (CуммаНУОборотДТ) для каждой номенклатуры она должна...

12
884 / 404 / 174
Регистрация: 20.10.2016
Сообщений: 1,828
24.10.2016, 11:29 2
Для начала я бы проверил расстановку скобок, ибо там просто атас творится.

Delphi
1
2
3
4
5
6
7
8
9
10
11
12
var st:String;
..
begin
st := 'SELECT * FROM Zayavki WHERE (';
st := st + '((DataSozd>=:Dat1) AND (DataSozd<=:Dat2)) ';
st := st + ' OR ';
st := st + '((DataSozd<=:Dat1) AND (Sostoyanie=' + QuotedStr('Не выполнено') + ') AND (ShhetchikKopij>0)';
st := st + ' OR ';
st := st + '((Sostoyanie=' + QuotedStr('Выполнено') + ') AND (DataVypoln Is Not Null) And (DataVypoln>=:Dat3) AND (ShhetchikKopij>0))';
ADOQuery1.SQL.Text := st;
..
end;
Во-вторых, у вас в базе строки "Выполнено" и "Не выполнено" хранятся в кавычках?
0
0 / 0 / 0
Регистрация: 23.07.2013
Сообщений: 50
24.10.2016, 11:32  [ТС] 3
Добавлено через 1 минуту
Проверил уже раз 100500. Благо Делфи подсвечивает их
0
884 / 404 / 174
Регистрация: 20.10.2016
Сообщений: 1,828
24.10.2016, 11:34 4
Так, я в своем коде забыл поставить последнюю скобку в запрос. Запросы с раздельными условиями в студию.
0
0 / 0 / 0
Регистрация: 23.07.2013
Сообщений: 50
24.10.2016, 11:34  [ТС] 5
Нет. Там, где значения Выполнено и Не выполнено - это текстовое поле
0
884 / 404 / 174
Регистрация: 20.10.2016
Сообщений: 1,828
24.10.2016, 11:48 6
Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
var st:String;
..
begin
st := 'SELECT * FROM Zayavki WHERE (';
st := st + '((DataSozd>=:Dat1) AND (DataSozd<=:Dat2)) ';
st := st + ' OR ';
st := st + '((DataSozd<=:Dat1) AND (Sostoyanie=:nvp) AND (ShhetchikKopij>0)';
st := st + ' OR ';
st := st + '((Sostoyanie=:vp) AND (DataVypoln Is Not Null) And (DataVypoln>=:Dat3) AND (ShhetchikKopij>0))';
st := st +')';
ADOQuery1.SQL.Text := st;
ADOQuery1.Parameters.ParamByName('vp').Value := 'Выполнено';
ADOQuery1.Parameters.ParamByName('nvp').Value := 'Не выполнено';
..
end;
Все еще жду код с раздельными условиями.
0
0 / 0 / 0
Регистрация: 23.07.2013
Сообщений: 50
24.10.2016, 12:51  [ТС] 7
1 запрос:

SQL
1
2
3
4
5
'Select * From Zayavki Where (
((DataSozd<=:Dat1) And (ShhetchikKopij>0) And 
    ((Sostoyanie=' + QuotedStr('Не выполнено') + ') Or 
    ((Sostoyanie=' + QuotedStr('Выполнено') + ') And (DataVypoln Is Not Null) And (DataVypoln>=:Dat1))) )
);'
2 запрос:

SQL
1
'Select * From Zayavki Where ((DataSozd>=:Dat1) And (DataSozd<=:Dat2));'
По-отдельности оба они работают. Каждый выдаёт свои записи. Но если пытаюсь соединить их в одну строку запроса с помощью Or , то срабатывает только тот запрос, который стоит первым в этой строке.
0
884 / 404 / 174
Регистрация: 20.10.2016
Сообщений: 1,828
24.10.2016, 13:25 8
Попробуйте, все же, применить этот код:

Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
var st:String;
..
begin
st := 'SELECT * FROM Zayavki WHERE (';
st := st + '((DataSozd>=:Dat1) AND (DataSozd<=:Dat2))';
st := st + ' OR ';
st := st + '((DataSozd<=:Dat1) AND (Sostoyanie=:nvp) AND (ShhetchikKopij>0))';
st := st + ' OR ';
st := st + '((Sostoyanie=:vp) AND (DataVypoln Is Not Null) And (DataVypoln>=:Dat3) AND (ShhetchikKopij>0))';
st := st +')';
ADOQuery1.SQL.Text := st;
ADOQuery1.Parameters.ParamByName('vp').Value := 'Выполнено';
ADOQuery1.Parameters.ParamByName('nvp').Value := 'Не выполнено';
..
end;
Он хоть и нагляднее, чем код выше, но и то я со скобками путаюсь. Исключим человеческий фактор.
0
0 / 0 / 0
Регистрация: 23.07.2013
Сообщений: 50
25.10.2016, 02:10  [ТС] 9
Ничего не изменилось.

Добавлено через 46 минут
Я почти не знаю SQL. Разбираюсь с ним по мере написания проги. Я так понимаю тут надо что-то с Union прописывать в запросе.
0
884 / 404 / 174
Регистрация: 20.10.2016
Сообщений: 1,828
25.10.2016, 09:07 10
Скиньте получившийся код.

UNION сам по себе работает просто: он объединяет результаты двух сходных запросов:

SQL
1
2
3
4
5
(SELECT * FROM Zayavki WHERE (
((DataSozd<=:Dat1) AND (ShhetchikKopij>0) AND 
    ((Sostoyanie=' + QuotedStr('Не выполнено') + ') OR 
    ((Sostoyanie=' + QuotedStr('Выполнено') + ') AND (DataVypoln IS NOT NULL) AND (DataVypoln>=:Dat1))) )
))UNION(SELECT * FROM Zayavki WHERE ((DataSozd>=:Dat1) AND (DataSozd<=:Dat2)));
0
0 / 0 / 0
Регистрация: 23.07.2013
Сообщений: 50
25.10.2016, 23:06  [ТС] 11
Спасибо. Сам разобрался. Причина крылась в том, что если в запросе параметр с одним и тем же именем встречается во 2 и более раз, то он игнорируется. Пришлось создавать аж 4 параметра и присваивать им одну и ту же переменную. Это же нерационально! У них какая-то хрень с параметрами ещё с Делфи 7 идёт, а вроде ведь солидная контора эта...Borland, щас Embarcadero или как их там...
0
Nanotentacle
26.10.2016, 07:19
  #12

Не по теме:

KAV1989, думаю, это чем-то обусловлено, о чем мы не догадываемся. Я слишком далек от того, чтобы считать людей, которые могут написать компонент работы с базой данных, которым пользуется куча людей, настолько невнимательными, что они будут допускать подобные ошибки. Скорее всего, какая-то специфика.

0
0 / 0 / 3
Регистрация: 21.09.2015
Сообщений: 135
26.10.2016, 18:15 13
Цитата Сообщение от Nanotentacle Посмотреть сообщение
Скорее всего, какая-то специфика.

Не по теме:

Ага, было дело в делфи проблемы с Access, до сих пор не понял синтаксиса, каждый JOIN обрамлять в скобочки...

Кликните здесь для просмотра всего текста
Delphi
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
ADOQuery1.SQL.Text:= ('SELECT trp.therapy_name, cl.first_name, cl.client_name, cl.last_name,' +
                             'a.nickname, doc.first_name,' +
                             'a.animal_id,' +
                             'cl.client_id,' +
                             'doc.doctor_id,' +
                             'dg.diagnosis_id,' +
                             'trp.therapy_id ' +
                      'FROM ( ' +  { 1 }
                            '( ' +  { 2  }
                             '( ' +  { 3 }
                              '(animals a ' +
                      'INNER JOIN ' +
                        'clients cl ' +
                      'ON ' +
                        'cl.client_id = a.client_id_ref) ' +
                      'INNER JOIN ' +
                        'doctors doc ' +
                      'ON ' +
                        'doc.doctor_id = a.doctor_id_ref) ' +
                      'INNER JOIN ' +
                        'diagnosis dg '  +
                      'ON ' +
                        'dg.diagnosis_id = a.diagnosis_id_ref)' +
                      'INNER JOIN ' +
                        'therapy trp ' +
                      'ON ' +
                        'a.animal_id = trp.animal_id_ref)');

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

SQL запрос, работающий в MS SQL Menegment'e не работает в делфи
Требуется выполнить запрос по нажатию кнопки, запрос сначала написал в Microsoft SQL Managment, где...

Не работае запрос в SQL Navigator 6.0 хотя работает в 4 и SQL Plus
Добрый день. Такая вот непонятная проблемка нарисовалась на ровном месте. Установили SQL...

Не работает UBS-порты, нужен дельный совет
Всем доброго время суток! Описываю проблему/ситуацию: 1) На самом системном блоке есть 2 UBS...

Использование shell_exec() в ubuntu 10.04 (не работает, нужен совет)
И снова вынужден обратиться за помощью: server apache2, php5, на базе ubuntu 10.04 необходимо...


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

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