1

Тема: Робота з діапазонами дат (Оракл)

Написати процедуру, що зберігається з параметрами, що визначають діапазон дат випуску книг. процедура
дозволяє оновити дані про тираж випуску книг за наступними умовами:
- • Якщо дата випуску книги знаходиться в певному діапазоні, тоді кількість сторінок потрібно збільшити в два рази, а ціну за одиницю збільшити на 20%;
- • Якщо дата випуску книги не входить в діапазон, тоді тираж залишити без змін.
Передбачити висновок на екран відповідних повідомлень про помилку, якщо передані дати однакові,
або кінцева дата меньша від початкової дати, або ж початкова дата більша поточної дати

create or replace procedure Book_update(start_date date, end_date date)
as
begin
if min(b.DATE_OF_PUBLISH)=max(b.DATE_OF_PUBLISH) then 
RAISE_APPLICATION_ERROR(200,'Дата початку та дата кінця однакові');
elsif start_date>end_date then 
RAISE_APPLICATION_ERROR(201,'Дата початку більша ніж дата кінця');
elsif start_date>sysdate then 
RAISE_APPLICATION_ERROR(202,'Дата початку більша ніж сьогоднішня дата');
update BOOKS set PRICE=PRICE*1.1,PAGES=PAGES*2
where start_date=min(DATE_OF_PUBLISH)and end_date=max(DATE_OF_PUBLISH)and DATE_OF_PUBLISH
between start_date and end_date;

update BOOKS set set PRICE=PRICE*1.1
where start_date=min(DATE_OF_PUBLISH)and end_date=max(DATE_OF_PUBLISH)and DATE_OF_PUBLISH
not between start_date and end_date; 
end if;
end;

Помилки:

PL/SQL: SQL Statement ignored
11/18     PL/SQL: ORA-00934: group function is not allowed here
14/1      PL/SQL: SQL Statement ignored
14/18     PL/SQL: ORA-01747: invalid user.table.column, table.column, or column specification
Errors: check compiler log

2

Re: Робота з діапазонами дат (Оракл)

create or replace procedure Book_update(start_date date, end_date date)
as
begin
if min(DATE_OF_PUBLISH)=max(DATE_OF_PUBLISH) then 
RAISE_APPLICATION_ERROR(200,'Дата початку та дата кінця однакові');
elsif start_date>end_date then 
RAISE_APPLICATION_ERROR(201,'Дата початку більша ніж дата кінця');
elsif min(DATE_OF_PUBLISH)>systimestamp then 
RAISE_APPLICATION_ERROR(202,'Дата початку більша ніж сьогоднішня дата');
update BOOKS set PRICE=PRICE*1.1,PAGES=PAGES*2
where start_date in (select min(DATE_OF_PUBLISH)from BOOKS )and end_date in (select max(DATE_OF_PUBLISH)from BOOKS)and DATE_OF_PUBLISH
between start_date and end_date;

update BOOKS set set PRICE=PRICE*1.1
where start_date=min(DATE_OF_PUBLISH)and end_date=max(DATE_OF_PUBLISH)and DATE_OF_PUBLISH
not between start_date and end_date; 
end if;
end;

Помилка:

PL/SQL: SQL Statement ignored
PL/SQL: ORA-01747: invalid user.table.column, table.column, or column specification
Errors: check compiler log

3

Re: Робота з діапазонами дат (Оракл)

create or replace procedure Book_update(start_date date, end_date date)
as
begin
if min(DATE_OF_PUBLISH)=max(DATE_OF_PUBLISH) then 
RAISE_APPLICATION_ERROR(200,'Дата початку та дата кінця однакові');
elsif start_date>end_date then 
RAISE_APPLICATION_ERROR(201,'Дата початку більша ніж дата кінця');
elsif min(DATE_OF_PUBLISH)>systimestamp then 
RAISE_APPLICATION_ERROR(202,'Дата початку більша ніж сьогоднішня дата');

update BOOKS set PRICE=PRICE*1.1
where start_date in (select min(DATE_OF_PUBLISH)from BOOKS )and end_date in (select max(DATE_OF_PUBLISH)from BOOKS)and DATE_OF_PUBLISH
between start_date and end_date;

update BOOKS set PAGES=PAGES*2
where start_date in (select min(DATE_OF_PUBLISH)from BOOKS )and end_date in (select max(DATE_OF_PUBLISH)from BOOKS)and DATE_OF_PUBLISH
between start_date and end_date;

update BOOKS set PRICE=PRICE*1.1
where start_date in (select min(DATE_OF_PUBLISH) from Books)and end_date in (select max(DATE_OF_PUBLISH)from Books)and DATE_OF_PUBLISH
not between start_date and end_date; 
end if;
end;
PL/SQL: Statement ignored
     PLS-00204: function or pseudo-column 'MIN' may be used inside a SQL statement only
Errors: check compiler log

4

Re: Робота з діапазонами дат (Оракл)

Дивлячись на назву вхідних параметрів і на цю умову

if min(DATE_OF_PUBLISH)=max(DATE_OF_PUBLISH) then 
RAISE_APPLICATION_ERROR(200,'Дата початку та дата кінця однакові');

підозрюю, що тут повинно бути просто

if start_date=end_date then 
RAISE_APPLICATION_ERROR(200,'Дата початку та дата кінця однакові');

(і далі по тексту аналогічно)...

5

Re: Робота з діапазонами дат (Оракл)

Відкомпілювало, але дані в таблиці не змінились після виконання процедури

create or replace procedure Book_update(start_date date, end_date date)
as
begin
if start_date=end_date then 
RAISE_APPLICATION_ERROR(200,'Дата початку та дата кінця однакові');
elsif start_date>end_date then 
RAISE_APPLICATION_ERROR(201,'Дата початку більша ніж дата кінця');
elsif start_date>systimestamp then 
RAISE_APPLICATION_ERROR(202,'Дата початку більша ніж сьогоднішня дата');

update BOOKS set PRICE=PRICE*1.1
where start_date=(select min(DATE_OF_PUBLISH)from BOOKS )and end_date=(select max(DATE_OF_PUBLISH)from BOOKS)and DATE_OF_PUBLISH
between start_date and end_date;

update BOOKS set PAGES=PAGES*2
where start_date=(select min(DATE_OF_PUBLISH)from BOOKS )and end_date=(select max(DATE_OF_PUBLISH)from BOOKS)and DATE_OF_PUBLISH
between start_date and end_date;

update BOOKS set PRICE=PRICE*1.1
where start_date=(select min(DATE_OF_PUBLISH)as min_date from Books )and end_date=(select max(DATE_OF_PUBLISH) as max_date from Books)and DATE_OF_PUBLISH
not between start_date and end_date; 
end if;
end;
SET SERVEROUTPUT ON
  exec Book_update('26.10.2016','27.10.2016');
 

6

Re: Робота з діапазонами дат (Оракл)

Тут питання до даних в таблиці Books - які там наявні значення в колонці DATE_OF_PUBLISH ?

7

Re: Робота з діапазонами дат (Оракл)

Стояла дата 26.10.2016

exec Book_update('25.10.2016','27.10.2016');

всеодно нічого не змінюється

8

Re: Робота з діапазонами дат (Оракл)

переробив трохи код, але дані в таблиці не змінились.

create or replace procedure Book_update(start_date date, end_date date)
as
publishing_date date;
begin
if start_date=end_date then 
RAISE_APPLICATION_ERROR(200,'Дата початку та дата кінця однакові');
elsif start_date>end_date then 
RAISE_APPLICATION_ERROR(201,'Дата початку більша ніж дата кінця');
elsif start_date>systimestamp then 
RAISE_APPLICATION_ERROR(202,'Дата початку більша ніж сьогоднішня дата');
if publishing_date
between start_date and end_date then 
update BOOKS set PRICE=PRICE*1.1
where start_date=(select min(DATE_OF_PUBLISH)from BOOKS )and end_date=(select max(DATE_OF_PUBLISH)from BOOKS)and DATE_OF_PUBLISH
between start_date and end_date;
if publishing_date
between start_date and end_date then 
update BOOKS set PAGES=PAGES*2
where start_date=(select min(DATE_OF_PUBLISH)from BOOKS )and end_date=(select max(DATE_OF_PUBLISH)from BOOKS)and DATE_OF_PUBLISH
between start_date and end_date;
if publishing_date
not between start_date and end_date then 
update BOOKS set PRICE=PRICE*1.1
where start_date=(select min(DATE_OF_PUBLISH)as min_date from Books )and end_date=(select max(DATE_OF_PUBLISH) as max_date from Books)and DATE_OF_PUBLISH
not between start_date and end_date and publishing_date=DATE_OF_PUBLISH; 
end if;
end if;
end if;
end if;
end;
SET SERVEROUTPUT ON
  exec Book_update('25.10.2016','27.10.2016');
 

9

Re: Робота з діапазонами дат (Оракл)

Підкажіть будь-ласка!!! Компілюється, але дані в таблиці не змінюються. Я вибрав дати для зміни даних однієї книги.

create or replace procedure Book_update(start_date date, end_date date)
as
publishing_date date;
begin
if start_date=end_date then 
RAISE_APPLICATION_ERROR(200,'Дата початку та дата кінця однакові');
elsif start_date>end_date then 
RAISE_APPLICATION_ERROR(201,'Дата початку більша ніж дата кінця');
elsif start_date>systimestamp then 
RAISE_APPLICATION_ERROR(202,'Дата початку більша ніж сьогоднішня дата');
if publishing_date
between start_date and end_date then 
update BOOKS set PRICE=(PRICE*1.1),PAGES=(PAGES*2)
where start_date=DATE_OF_PUBLISH and end_date=DATE_OF_PUBLISH and DATE_OF_PUBLISH
between start_date and end_date 
and publishing_date=DATE_OF_PUBLISH;
if publishing_date
not between start_date and end_date then 
update BOOKS set PRICE=(PRICE*1.1)
where start_date=DATE_OF_PUBLISH and end_date=DATE_OF_PUBLISH and DATE_OF_PUBLISH
not between start_date and end_date 
and publishing_date=DATE_OF_PUBLISH; 
end if;
end if;
end if;
end;
SET SERVEROUTPUT ON
exec Book_update('20.10.2016','27.10.2016');
 

10

Re: Робота з діапазонами дат (Оракл)

Ви б відступи розставили, так читати боляче.
І підкажіть, будь ласка, у вас є

publishing_date date;

а потім ви перевіряєте

if publishing_date between start_date and end_date then 

Що саме має бути в таблиці чи в параметрах, щоб ця умова виконалася?

Подякували: leofun011

11

Re: Робота з діапазонами дат (Оракл)

Зробив так, але процедура нічого не міняє

create or replace procedure Book_update(start_date date, end_date date)
as
begin
if start_date=end_date then 
RAISE_APPLICATION_ERROR(200,'Дата початку та дата кінця однакові');
elsif start_date>end_date then 
RAISE_APPLICATION_ERROR(201,'Дата початку більша ніж дата кінця');
elsif start_date>systimestamp then 
RAISE_APPLICATION_ERROR(202,'Дата початку більша ніж сьогоднішня дата');
update BOOKS set PRICE=PRICE*1.1,PAGES=PAGES*2
where start_date=DATE_OF_PUBLISH and end_date=DATE_OF_PUBLISH and DATE_OF_PUBLISH
between start_date and end_date; 
update BOOKS set PRICE=PRICE*1.1
where start_date=DATE_OF_PUBLISH and end_date=DATE_OF_PUBLISH and DATE_OF_PUBLISH
not between start_date and end_date; 
end if;
end;

12

Re: Робота з діапазонами дат (Оракл)

sasha87 написав:
where start_date=DATE_OF_PUBLISH and end_date=DATE_OF_PUBLISH and DATE_OF_PUBLISH
between start_date and end_date; 

Можете навести приклад таких значень start_date, end_date та DATE_OF_PUBLISH, коли ця умова виконується?

Подякували: leofun011

13

Re: Робота з діапазонами дат (Оракл)

Наприклад: мені потрібно змінити дані для книги, дата публікації якої 26.10.2016 -  DATE_OF_PUBLISH.
я беру діапазон 20.10.2017 - start_date і 27.10.2017 - end_date. тобто книга входить в діапазон і дані в строці повинні були би змінитись. Але не можу  зрозуміти, чому вони не змінюються, не можу знайти помилку.
  start_date=DATE_OF_PUBLISH - значення start_date має братись з стовпчика DATE_OF_PUBLISH

14

Re: Робота з діапазонами дат (Оракл)

Підставимо наведені вами значення у ваш вираз:

where '20.10.2017'='26.10.2016' and '27.10.2017'='26.10.2016'
and '26.10.2016' between '20.10.2017' and '27.10.2017'; 

Скажіть, ви знаєте, яке буде значення виразу '20.10.2017'='26.10.2016' і як працює булевий оператор AND?

15

Re: Робота з діапазонами дат (Оракл)

тобто перевіряються усі умови.

16

Re: Робота з діапазонами дат (Оракл)

Тобто спробуйте обидва однакові вхідні параметри:

26.10.2016

17

Re: Робота з діапазонами дат (Оракл)

видасть код помилки  - 200

RAISE_APPLICATION_ERROR(200,'Дата початку та дата кінця однакові');

18

Re: Робота з діапазонами дат (Оракл)

то як зробити, щоб дані змінились?

19

Re: Робота з діапазонами дат (Оракл)

Може, спробуєте відповісти на першу частину мого питання? Вона нескладна, і я відверто не можу зрозуміти, чому ви цього не бачите.

20

Re: Робота з діапазонами дат (Оракл)

koala написав:

Підставимо наведені вами значення у ваш вираз:

where '20.10.2017'='26.10.2016' and '27.10.2017'='26.10.2016'
and '26.10.2016' between '20.10.2017' and '27.10.2017'; 

Скажіть, ви знаєте, яке буде значення виразу '20.10.2017'='26.10.2016' і як працює булевий оператор AND?

Видасть помилку, тому що початкова дата діапазону більша від кінцевої дати.