Главная страница
Top.Mail.Ru    Яндекс.Метрика
Текущий архив: 2007.10.07;
Скачать: CL | DM;

Вниз

Вопрос по БД   Найти похожие ветки 

 
Progr   (2007-09-06 21:07) [0]

Доброго времени суток, мастера.
Возник один вопрос, который я не могу понять. Пишу небольшую БД, исходный файл БД в IB. Использую IBquery компонент. Так Вот, почему:
{select * from ANM_Saon
Where (CHISLO >= :data1 and CHISLO <= :data2)  and
(int1 = :Tint1)    and
(int2 = :Tint2)   and
(int3 = :Tint3)  and
(int4 = :Tint4)    and
(int5= :Tint5)}    этот код не делает выборку. CHISLO типа DATE, а все остальные поля int1-5 SmallINT. Все параметизированные данные задаю верно. Но выборки нет. А вот код:
{select * from ANM_Saon
Where (CHISLO >= :data1 and CHISLO <= :data2)  
Union
select * from ANM_Saon where
(int1 = :Tint1)    and
(int2 = :Tint2)   and
(int3 = :Tint3)  and
(int4 = :Tint4)    and
(int5= :Tint5)}  
работает. Причем не всегда правильно. Я обратил внимание если data1=data2 то условия в секции Union не используются.
Если честно, то первый вариант мне больлше нравится, так как в запросе  при построении запроса на выборку фильтр использует все переменные.
Не подскажите, мастера, что я делаю не так, почему первый код не работоспособен .
Заранее благодарю. С уважением...


 
Anatoly Podgoretsky ©   (2007-09-06 21:13) [1]

> Progr  (06.09.2007 21:07:00)  [0]

Первый код не работает, поскольку нет записей удовлетворяющих условию.


 
Desdechado ©   (2007-09-06 21:30) [2]

Нужно быть осторожным с типом SMALLINT, т.к. параметры нужно явно типизироватьи явно присваивать так, чтоб не получилось, например, как будто это Integer.

Секции UNION не существует. Это способ объединения результатов двух запросов. Т.о. 1-й и 2-й код делают совершенно разные вещи:
1. выбирает то, что удовлетворяет обоим условиям
2. выбирает то, что удовлетворяет только 1-му условию, а затем дополняет результат тем, что удовлетворяет только 2-му условию


 
Progr   (2007-09-06 21:38) [3]

>>> Первый код не работает, поскольку нет записей удовлетворяющих условию.

Но почему. Если я задаю между 10.08.07 и 10.09.07.
Поля в базе int принимают либо 1 либо 0. Соответственно на форме в программе ввожу эти переменные. Но в базе есть запись удовлетворяющая этому условию.
поле:
CHISLO     int1  int2   int3   int4   int5
15.08.07.  1       0       1      0      0
База сама шире. Есть дополнительные поля, которые я здесь не привожу так фильтрация по ним не происходит.
Я соответственно в запрос передаю параметры int1-5 и дату соответствующие данной записи. Параметры, передаваемые в запрос, удовлетворяют условию приведенной выше записи. То есть должна вернуться выборка состоящая из этой записи.

Так почему не работает?
С уважением..


 
MsGuns ©   (2007-09-06 21:40) [4]

В дате сеть еще время


 
Progr   (2007-09-06 21:50) [5]

>>>В дате сеть еще время

Не понял. Расшифруйте пожалуйста.
С уважением.

А почему тогда второй работает при таких же условиях


 
MsGuns ©   (2007-09-06 21:54) [6]

>Progr   (06.09.07 21:50) [5]
>Не понял. Расшифруйте пожалуйста.
>С уважением.

Запрос типа
Select ..
  where FDate=:p1

с ParamByName("p1").asDate := NOW

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

Все дело во времени - hh:mm:ss


 
MsGuns ©   (2007-09-06 21:57) [7]

Надо указывать либо >=[<Дата> 00:00:00] and <=[<Дата> 23:59:59]
либо использовать функции преобразования чтобы сверять только числа, но не время


 
Anatoly Podgoretsky ©   (2007-09-06 22:05) [8]

> Progr  (06.09.2007 21:50:05)  [5]

Ты сам написал, что не работает (не всегда именно это и означает)
Повторяю еще раз, нет записей под условие.
Это и доказывает второй пример.
Запись с датой есть, а с INT нет
При первом примере это явно видно.


 
Anatoly Podgoretsky ©   (2007-09-06 22:08) [9]

> MsGuns  (06.09.2007 21:54:06)  [6]

В даннои случае это не так, кроме граничных условий.
D >= :D1 and D <=:D2

Зато там еще куча AND, должны выполниться все условия, а ту еще и SmallInt в придачу.
К вопросу не приложен DDL, точное значение параметров и записи которые якобы должны быть выданы.


 
Progr   (2007-09-06 22:09) [10]

Var
a: Tdate;

...
ParamByName("data1").asDate := a;

Так у меня в программе, тип переменной явное TDate.
Это получается что в переменную заносится еще и время, интересно.

может подскажите тогда как преобразуется первый код.
С уважением.


 
Progr   (2007-09-06 22:28) [11]

Давайте я попробую привести код:
Var
 firstdate: TDate;
 secondate: TDate;
 int1: smallint;
 int2: smallint;
 int3: smallint;
 int4: smallint;
 int5: smallint;
 

begin

 Firstdate := dt1.Date;  
 Secondate := dt2.Date; (Tdatetimepicker-переведен в Date)

 if box1.Checked     then int1:=1   else int1:=0;
 if box2.Checked     then int2:=1   else int2:=0;
 if box3.Checked     then int3:=1   else int3:=0;
 if box4.Checked     then int4:=1   else int4:=0;
 if box5.Checked     then int5:=1   else int5:=0;

IB.Close;
IB.ParamByName("data1").AsDate      := Firstdate;
IB.ParamByName("data2").AsDate      := Secondate;
IB.ParamByName("tint1").AsSmallInt   := int1;
IB.ParamByName("tint2").AsSmallInt   := int2;
IB.ParamByName("tint3").AsSmallInt   := int3;
IB.ParamByName("tint4").AsSmallInt   := int4;
IB.ParamByName("tint5").AsSmallInt   := int5;
IB.Open;

end;

Код поиска в первом сообщении.

Теперь сама таблица в IB:
CREATE TABLE ANM_SAON(ID NUMERIC(6,0) NOT NULL PRIMARY KEY, CHISLO DATE, VREMYA TIME, VL530 INTEGER, PRICHINA VARCHAR(350), INT1 SMALLINT, INT2 SMALLINT, INT3 SMALLINT, INT4 SMALLINT, INT5 SMALLINT, PRIMECHANIE VARCHAR(350))

Вот пожалуй основные исходные данные.
С вводом, редактированием, удалением записей все работает.
А вот с выборкой вот такая проблема.


 
Anatoly Podgoretsky ©   (2007-09-06 22:36) [12]

> Progr  (06.09.2007 22:09:10)  [10]

Посмотри описания тип TDate, будешь удивлен.


 
Anatoly Podgoretsky ©   (2007-09-06 22:43) [13]

> Progr  (06.09.2007 22:28:11)  [11]

> Firstdate := dt1.Date;  
> Secondate := dt2.Date; (Tdatetimepicker-переведен в Date)

Это ни о чем не говорит, какие то неясные переменные, с неясными значениями. Если писать, то так

Firstdate := Trunc(dt1.Date);  
Secondate := Trunc(dt2.Date) + 1;

и условие заменить на Secondate < :Secondate, ведь ты же хочешь любую дату, например 15.09.2007 23:00:00 а не только 15.09.2007 00:00:00 - это типичная ошибка при работе с датами.

По второй дате, ведь


 
Progr   (2007-09-06 22:45) [14]

Не сможете подкинуть ссылочку, в моей лит-ре слабо описан тип TDate.


 
Anatoly Podgoretsky ©   (2007-09-06 22:47) [15]

> Progr  (06.09.2007 22:45:14)  [14]

Не надо литературе, это в исходника и возможно в справке

TDate = TDateTime;
TTime = TDateTime;


 
Progr   (2007-09-06 23:37) [16]

>>>Anatoly Podgoretsky ©   (06.09.07 22:43) [13]

попробую сделать


 
Anatoly Podgoretsky ©   (2007-09-06 23:44) [17]

Может это тебе и не поможет, точнее точно не поможет, но именно так надо работать с интервалами, которые включают время.

Trunc(StartDate) >= and < Trunc(EndDate) + 1


 
Progr   (2007-09-07 00:02) [18]

Кстати, еще один момент
Когда я убираю операции AND с полями int, условие прекрасно работает, и выборку выдает правильно по всем записям.
Но если я добавляю хоть один элемент AND для значения int, то согласно логике оно тоже должно выполняться.


 
MsGuns ©   (2007-09-07 00:17) [19]

НАсколько я помню, в ИВ нет типа "Дата", а есть только "Дата-время" и таймстамп


 
Washington ©   (2007-09-07 15:21) [20]

Получение даты в формате дд.мм.гггг:

var
time:TSystemTime;
date:TDateTime;
begin
GetSystemTime(time);
date:=SystemTimeToDateTime(time);
end;

Вроде так, у меня всё нормально пахает


 
Progr   (2007-09-07 20:11) [21]

>>>Washington ©   (07.09.07 15:21) [20]

Простите. То есть мне желательно в столбец CHISLO типа Date вносить дату обработанную Вашим кодом? Или этого кода достаточно, чтобы правильно построить выборку?

Потому что я так понял из рассуждений выше, что  в поле базы вносится как дата, так и время?


 
Desdechado ©   (2007-09-07 20:25) [22]

> НАсколько я помню, в ИВ нет типа "Дата", а есть только "Дата-время" и таймстамп
В разных диалектах по-разному.
В 3-м TIMESTAMP - это комбинация, но есть и независимые дата и время. Судя по DDL таблицы автора, у него 3-й диалект.


 
Progr   (2007-09-07 21:14) [23]

Хорошо. А есть способ, скажем сделать так:
1. Делаю выборку по дате. Она работает вроде правильно.
2. А из полученного Readonly таблицы осуществить выборку по полям int.
Тогда вроде может заработать.

Возможно это сделать одним запросом.
Или надо 2 запроса строить.
Еслди 2 то как тогда быть, создавать виртуальную таблицу?


 
Desdechado ©   (2007-09-07 22:09) [24]

Все можно из [0] сделать одним запросом.


 
Progr   (2007-09-07 22:53) [25]

Не подскажите каким образом мне построить запрос.
Я просто новичок и не сразу все схватываю.
С уважением...


 
Progr   (2007-09-11 21:16) [26]

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

С уважением.


 
sniknik ©   (2007-09-12 11:02) [27]

а после всех экспериментов ты хоть что нибудь из посоветованного реализовал? учёл время,  поменял код, как он теперь выглядит?

кстати в [0] условие первого запроса далеко не тоже самое что во втором...
там ближе было бы поставить or вместо and между первым условием и кучкой остальных.
а так запрос верный (по сути а не по логике которую ты от него ожидаешь и которая нам неизвестна), просто нет нужных данных, впрочем см. [1].


 
Progr   (2007-09-12 20:21) [28]

Спасибо всем.
Вроде получилось пока.
Использовал Trunc, и нашел некоторый глюк который исправил.
Спасибо еще раз.



Страницы: 1 вся ветка

Текущий архив: 2007.10.07;
Скачать: CL | DM;

Наверх




Память: 0.54 MB
Время: 0.022 c
2-1189493063
tomkat
2007-09-11 10:44
2007.10.07
поиск подкаталогов


2-1189192064
Dmitriy_
2007-09-07 23:07
2007.10.07
Прозрачная форма, но в фокусе?


2-1189176135
*Ray*
2007-09-07 18:42
2007.10.07
Удалить подстроку из очень большой строки (больше 2 ГБ )


4-1175760398
kalexi
2007-04-05 12:06
2007.10.07
Создание приложений на чистом API - TPanel


2-1189525881
newanat
2007-09-11 19:51
2007.10.07
TListView про сортировку