powered by simpleCommunicator - 2.0.61     © 2026 Programmizd 02
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Форумы / Oracle [игнор отключен] [закрыт для гостей] / Значение в виде даты
32 сообщений из 32, показаны все 2 страниц
Значение в виде даты
    #39434442
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Добрый вечер. Имеется огромная таблица "График" с полями код сотрудника, год, и N1-N52, олицетворяющие 52 недели в году. У какого нибудь N (например N1-N5) стоит значение у, что обозначает учебный отпуск. Всё это достигается путём динамического перебора столбцов и выявления тех, где стоит значение у, причём в виде даты. Например, с 1 января по 26 января. Беда в том, что имеющаяся функция переделывания из N1 в Дату не смотрит на то, как начинаются недели в году. К примеру, в 2017 были недели 1 января, 2 января, 9 января (условие задачи - вне зависимости от года N1 начинается с 1 января). А функция пишет 1 января, 8 января и т.д., что не соответствует истине. То же самое и с другими годами.

Подскажите, что я не так делаю? Вот код.

Код: sql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
create or replace FUNCTION get_week_list3(i_code IN INTEGER, i_year in integer) RETURN VARCHAR2 IS
  l_list  VARCHAR2(32767);
  l_res   VARCHAR2(4000);
BEGIN
SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''|| to_char( trunc (to_date(i_year||'0101', 'yyyymmdd') 
+ ((LTRIM(column_name,'N'))-1)*7, 'ww'), 'dd mon')||''''|| '||''; '' ELSE NULL END ' ,'||') 
WITHIN GROUP(ORDER BY 1)
  INTO  l_list
  FROM  user_tab_columns
  WHERE TABLE_NAME = 'GRAFIK' 
  AND column_name LIKE 'N%';
EXECUTE IMMEDIATE 'SELECT '||l_list||' FROM GRAFIK WHERE kod_sotr=:A AND god=:year' INTO l_res USING i_code,i_year;
RETURN RTRIM(l_res);
END;



Сама функция преобразования в этой строке

Код: sql
1.
2.
SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''|| to_char( trunc (to_date(i_year||'0101', 'yyyymmdd') 
+ ((LTRIM(column_name,'N'))-1)*7, 'ww'), 'dd mon')||''''|| '||''; '' ELSE NULL END ' ,'||') 



Как сделать так, что было правильно?
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434462
stax..
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94,

ничего не понял с "в 2017 были недели 1 января, 2 января, 9 января "

приведите примеры (с разными годами, Nxxx-Nyyy)
ф-ция считет так, правильно так

первая неделя ВСЕГДА начинается 1-го января, вторая 8-го, и тд?

.......
stax
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434465
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
stax..ничего не понял с "в 2017 были недели 1 января, 2 января, 9 января "
приведите примеры (с разными годами, Nxxx-Nyyy)
ф-ция считет так, правильно так


То есть по задумке 1 неделя должна начинаться 1 января, полюбому. Например как в 2016 году. Там по сути 1 неделя должна начинаться с 1 января , 2 неделя с 4 января, 3 неделя - 11 января.

В 2017 году 1 января, 2 января, 9 января. Странно, но так и должно быть.
приведите примеры (с разными годами, Nxxx-Nyyy)
ф-ция считет так, правильно так

stax..первая неделя ВСЕГДА начинается 1-го января, вторая 8-го, и тд?
Да, эта функция при любом году начинает с 1 января, 2 неделю - с 8-го января, что не правильно. Если я ставлю 2017, то должно быть 1 января, 2 января, 9 января, и т.д.
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434467
Фотография -2-
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94,

iw и geatest
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434471
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
-2-iw и geatest

iw заместо ww подставлять? А geatest как связан? Он вроде наибольшее значение ищет.
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434523
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Norman94,

Вариант с iw хорошо помог, спасибо Вам! Теперь встал вопрос, как ему сказать, чтобы он прямо с 1 января считал?
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434529
Фотография Elic
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94Вариант с iw хорошо помог, спасибо Вам! Теперь встал вопрос, как ему сказать, чтобы он прямо с 1 января считал?А теперь прочитай и вторую половину ответа.
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434531
andreymx
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94Имеется огромная таблица "График" с полями код сотрудника, год, и N1-N52, олицетворяющие 52 недели в году.я такие таблицы анпивочу вьюхой
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434538
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Elic,

Не понимаю, как мне с помощью geatest, которая находит наибольшее значение, вычислить 1 января.
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434540
Фотография Elic
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94Не понимаю, как мне с помощью geatest, которая находит наибольшее значение, вычислить 1 января.а мне некуда ткнуть в
Norman94Вариант с iw хорошо помог
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434553
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Elic,

Вам бы книгу загадок писать

iw сделал всё грамотно, но первую неделю он представляет как 26 декабря, вторую - 2 января. Что не есть правда.
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434559
Фотография Elic
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94iw сделал всё грамотно, но первую неделю он представляет как 26 декабря, вторую - 2 января. Что не есть правда.Включи мозг и сравни каждую из этих дат на большинство с
Norman941 января
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434575
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Elic,

Попробую, но хоть убейте не могу понять как это мне поможет. Можете разжевать принцип?
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434678
Фотография Elic
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94Попробую, но хоть убейтеМожет и стоило,
Norman94не могу понять как это мне поможет. Можете разжевать принцип?чтобы не приумножать стадо не способных мыслить.
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434875
XMLer
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94Да, эта функция при любом году начинает с 1 января, 2 неделю - с 8-го января, что не правильно. Если я ставлю 2017, то должно быть 1 января, 2 января, 9 января, и т.д.
1 неделя любого года начинается с 1-го января, но это не всегда понедельник.
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434900
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434912
stax..
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94Elic,

Вам бы книгу загадок писать

iw сделал всё грамотно, но первую неделю он представляет как 26 декабря, вторую - 2 января. Что не есть правда.

Код: plsql
1.
2.
3.
4.
5.
6.
  1* select greatest(trunc(date '2017-01-01','IW'),date '2017-01-01') d from dual
SQL> /

D
--------
01.01.17



.....
stax
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434925
stax..
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94Norman94,
Добрый вечер. Имеется огромная таблица "График" с полями код сотрудника, год, и N1-N52, олицетворяющие 52 недели в году.


Вариант с iw хорошо помог, спасибо Вам! Теперь встал вопрос, как ему сказать, чтобы он прямо с 1 января считал?
ПОВТОРНО!



Вам уже писали для IW 53 недели (N53 у вашей нотации)
Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
SQL> select to_char(date '2020-12-31', 'IW') tyzhden6 from dual;

TYZHDEN6
----------
53

SQL> select to_char(date '2015-12-31', 'IW') tyzhden6 from dual;

TYZHDEN6
----------
53



.....
stax
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434953
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
stax..Norman94Elic,

Вам бы книгу загадок писать

iw сделал всё грамотно, но первую неделю он представляет как 26 декабря, вторую - 2 января. Что не есть правда.

Код: plsql
1.
2.
3.
4.
5.
6.
  1* select greatest(trunc(date '2017-01-01','IW'),date '2017-01-01') d from dual
SQL> /

D
--------
01.01.17



.....
stax

Ага, то есть используя greatest я высчитываю дату, потом сравниваю с датой 01 января определённого года. Значит, получается, будет так?

(SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''|| greatest(to_char( trunc (to_date(i_year||'0101', 'yyyymmdd')
+ ((LTRIM(column_name,'N'))-1)*7, 'ww'), 'dd mon'), date '2017-01-01')||''''|| '||''; '' ELSE NULL END ' ,'||')
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434954
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Elic,

Нужно больше иронии и ненависти, чтобы казаться умным.
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434980
Фотография Elic
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94Нужно больше иронии и ненависти, чтобы казаться умным.Это как-то уменьшит твою тугодумность?
...
Рейтинг: 0 / 0
Значение в виде даты
    #39434983
stax..
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94stax..пропущено...


Код: plsql
1.
2.
3.
4.
5.
6.
  1* select greatest(trunc(date '2017-01-01','IW'),date '2017-01-01') d from dual
SQL> /

D
--------
01.01.17



.....
stax

Ага, то есть используя greatest я высчитываю дату, потом сравниваю с датой 01 января определённого года. Значит, получается, будет так?

(SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''|| greatest(to_char( trunc (to_date(i_year||'0101', 'yyyymmdd')
+ ((LTRIM(column_name,'N'))-1)*7, 'ww'), 'dd mon'), date '2017-01-01')||''''|| '||''; '' ELSE NULL END ' ,'||')
1) константу date '2017-01-01 заменить на to_date(i_year||'0101', 'yyyymmdd')
2) определится ww или IW
3) имхо не там greatest, надо ...greatest(... , 'iw'),to_date(i_year||'0101', 'yyyymmdd'), 'dd mon')...
4) WITHIN GROUP(ORDER BY 1) ничего не сортирует
5) убедить шефа, что динамика сдесь не нужна

.....
stax
...
Рейтинг: 0 / 0
Значение в виде даты
    #39435002
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
stax..1) константу date '2017-01-01 заменить на to_date(i_year||'0101', 'yyyymmdd')
2) определится ww или IW
Всё таки iw, потому что с ним недели начинаются именно с тех чисел, что соответствует оному в определённому году.

stax..3) имхо не там greatest, надо ...greatest(... , 'iw'),to_date(i_year||'0101', 'yyyymmdd'), 'dd mon')...
4) WITHIN GROUP(ORDER BY 1) ничего не сортирует
5) убедить шефа, что динамика сдесь не нужна

Окей, сейчас попробую.
...
Рейтинг: 0 / 0
Значение в виде даты
    #39435008
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
stax..Norman94пропущено...


Ага, то есть используя greatest я высчитываю дату, потом сравниваю с датой 01 января определённого года. Значит, получается, будет так?

(SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''|| greatest(to_char( trunc (to_date(i_year||'0101', 'yyyymmdd')
+ ((LTRIM(column_name,'N'))-1)*7, 'ww'), 'dd mon'), date '2017-01-01')||''''|| '||''; '' ELSE NULL END ' ,'||')
1) константу date '2017-01-01 заменить на to_date(i_year||'0101', 'yyyymmdd')
2) определится ww или IW
3) имхо не там greatest, надо ...greatest(... , 'iw'),to_date(i_year||'0101', 'yyyymmdd'), 'dd mon')...
4) WITHIN GROUP(ORDER BY 1) ничего не сортирует
5) убедить шефа, что динамика сдесь не нужна

.....
stax

Написал как вы посоветовали

Код: sql
1.
2.
SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''|| to_char( trunc (greatest(to_date(i_year||'0101', 'yyyymmdd') 
+ ((LTRIM(column_name,'N'))-1)*7, 'iw'), to_date(i_year||'0101', 'yyyymmdd')), 'dd mon')||''''|| '||''; '' ELSE NULL END ' ,'||') 



Функция вылетает с ошибкой мол ожидался номер, а получил дату
...
Рейтинг: 0 / 0
Значение в виде даты
    #39435012
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
А попробовал так

Код: sql
1.
2.
SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''|| greatest(to_char( trunc (to_date(i_year||'0101', 'yyyymmdd') 
+ ((LTRIM(column_name,'N'))-1)*7, 'iw'), 'dd mon'), to_date(i_year||'0101', 'yyyymmdd'))||''''|| '||''; '' ELSE NULL END ' ,'||')



Как неделя с 26 декабря начиналась, так и начинается, эх(
...
Рейтинг: 0 / 0
Значение в виде даты
    #39435023
Фотография env
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94,

ты забавен
...
Рейтинг: 0 / 0
Значение в виде даты
    #39435024
Фотография env
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Если коротко

Norman94А попробовал так

Код: sql
1.
greatest(to_char( ..., 'dd mon'), to_date..., 'yyyymmdd'))




Дай-ка подумать, почему же '26 янв.' больше чем '20170101'?
...
Рейтинг: 0 / 0
Значение в виде даты
    #39435026
Фотография env
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
env,

*дек

* и не '20170101', а как NLS на душу положит
...
Рейтинг: 0 / 0
Значение в виде даты
    #39435031
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
envenv,

*дек

* и не '20170101', а как NLS на душу положит

Да я уже понял, что это не работает.

А вариант, который мне предложили, выдаёт ошибку
Код: sql
1.
2.
SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''|| to_char( trunc (greatest(to_date(i_year||'0101', 'yyyymmdd') 
+ ((LTRIM(column_name,'N'))-1)*7, 'iw'), to_date(i_year||'0101', 'yyyymmdd')), 'dd mon')||''''|| '||''; '' ELSE NULL END ' ,'||') 
...
Рейтинг: 0 / 0
Значение в виде даты
    #39435043
stax..
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94envenv,

*дек

* и не '20170101', а как NLS на душу положит

Да я уже понял, что это не работает.

А вариант, который мне предложили, выдаёт ошибку
Код: sql
1.
2.
SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''|| to_char( trunc (greatest(to_date(i_year||'0101', 'yyyymmdd') 
+ ((LTRIM(column_name,'N'))-1)*7, 'iw'), to_date(i_year||'0101', 'yyyymmdd')), 'dd mon')||''''|| '||''; '' ELSE NULL END ' ,'||') 



Код: plsql
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.
28.
29.
30.
31.
32.
33.
34.
SQL> ed
Wrote file afiedt.buf

  1  create or replace FUNCTION get_week_list3(i_code IN INTEGER, i_year in integer) RETURN VARCHAR2 IS
  2    l_list  VARCHAR2(32767);
  3    l_res   VARCHAR2(4000);
  4  BEGIN
  5  SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''||
  6           to_char(
  7              greatest(
  8                 trunc (to_date(i_year||'0101', 'yyyymmdd')+((LTRIM(column_name,'N'))-1)*7, 'iw')
  9                ,to_date(i_year||'0101', 'yyyymmdd'))
 10            ,'dd mon')||''''|| '||''; '' ELSE NULL END ' ,'||')
 11  WITHIN GROUP(ORDER BY 1)
 12    INTO  l_list
 13    FROM  user_tab_columns
 14    WHERE TABLE_NAME = 'GRAFIK'
 15    AND column_name LIKE 'N%';
 16  EXECUTE IMMEDIATE
 17    'SELECT '||l_list||' FROM GRAFIK
 18     WHERE kod_sotr=:A AND god=:year' INTO l_res USING i_code,i_year;
 19  RETURN RTRIM(l_res);
 20* END;
SQL> /

Function created.

SQL> select g.*,get_week_list3(KOD_SOTR,GOD) f from GRAFIK g;

       GOD   KOD_SOTR N N N N N N N N N N F
---------- ---------- - - - - - - - - - - ----------------------------------------
      2017        222 у   o o y o у o   o 01 січ; 06 лют;
      2017        202   у o o y o у o   o 02 січ; 06 лют;
      2017        111 o   у   y   у   o   09 січ; 06 лют;



зы
повторно
передайте шефу, WITHIN GROUP(ORDER BY 1) ничего не сортирует

.....
stax
...
Рейтинг: 0 / 0
Значение в виде даты
    #39435045
Norman94
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
stax..Norman94пропущено...


Да я уже понял, что это не работает.

А вариант, который мне предложили, выдаёт ошибку
Код: sql
1.
2.
SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''|| to_char( trunc (greatest(to_date(i_year||'0101', 'yyyymmdd') 
+ ((LTRIM(column_name,'N'))-1)*7, 'iw'), to_date(i_year||'0101', 'yyyymmdd')), 'dd mon')||''''|| '||''; '' ELSE NULL END ' ,'||') 




Код: plsql
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.
28.
29.
30.
31.
32.
33.
34.
SQL> ed
Wrote file afiedt.buf

  1  create or replace FUNCTION get_week_list3(i_code IN INTEGER, i_year in integer) RETURN VARCHAR2 IS
  2    l_list  VARCHAR2(32767);
  3    l_res   VARCHAR2(4000);
  4  BEGIN
  5  SELECT listagg('CASE WHEN '||column_name||' IN(''у'') THEN '||''''||
  6           to_char(
  7              greatest(
  8                 trunc (to_date(i_year||'0101', 'yyyymmdd')+((LTRIM(column_name,'N'))-1)*7, 'iw')
  9                ,to_date(i_year||'0101', 'yyyymmdd'))
 10            ,'dd mon')||''''|| '||''; '' ELSE NULL END ' ,'||')
 11  WITHIN GROUP(ORDER BY 1)
 12    INTO  l_list
 13    FROM  user_tab_columns
 14    WHERE TABLE_NAME = 'GRAFIK'
 15    AND column_name LIKE 'N%';
 16  EXECUTE IMMEDIATE
 17    'SELECT '||l_list||' FROM GRAFIK
 18     WHERE kod_sotr=:A AND god=:year' INTO l_res USING i_code,i_year;
 19  RETURN RTRIM(l_res);
 20* END;
SQL> /

Function created.

SQL> select g.*,get_week_list3(KOD_SOTR,GOD) f from GRAFIK g;

       GOD   KOD_SOTR N N N N N N N N N N F
---------- ---------- - - - - - - - - - - ----------------------------------------
      2017        222 у   o o y o у o   o 01 січ; 06 лют;
      2017        202   у o o y o у o   o 02 січ; 06 лют;
      2017        111 o   у   y   у   o   09 січ; 06 лют;




зы
повторно
передайте шефу, WITHIN GROUP(ORDER BY 1) ничего не сортирует

.....
stax

А, понял, не там ставил эту функцию. Теперь понял. Ещё раз, спасибо Вам!
...
Рейтинг: 0 / 0
Значение в виде даты
    #39435046
stax..
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Norman94А, понял, не там ставил эту функцию. Теперь понял. Ещё раз, спасибо Вам!
незачто
можно на ты

.....
stax
...
Рейтинг: 0 / 0
32 сообщений из 32, показаны все 2 страниц
Форумы / Oracle [игнор отключен] [закрыт для гостей] / Значение в виде даты
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]