Как поместить часть кода в виде строки в таблице, чтобы использовать ее в процедуре?

Я пытаюсь решить проблему ниже: мне нужно подготовить таблицу, которая состоит из 3 столбцов: user_id, значение месяца. Каждый из более чем 200 пользователей имеет различные значения параметров, которые определяют ожидаемое значение, а именно: LOB, CHANNEL, SUBSIDIARY. Поэтому я решил сохранить его в таблице ASYSTENT_GOALS_SET. Но я хотел избежать умножения строк и подумал, что было бы неплохо поместить все условия как часть кода, который я буду использовать в предложении "где" далее в процедуре. Итак, в качестве примера - вместо нескольких строк:

Я создал такую ​​запись:

До сих пор я создал таблицу тестирования ASYSTENT_TEST (где я собираю месяц и значение для определенного пользователя). Я написал часть процедуры, где я использовал BULK COLLECT.

declare
  type test_row is record
  (
  month NUMBER,
  value NUMBER
  );
  type test_tab is table of test_row;
  BULK_COLLECTOR test_tab;
  p_lob varchar2(10) :='GOSP';
  p_sub varchar2(14);
  p_ch varchar2(10) :='BR';
  begin
  select subsidiary into p_sub from ASYSTENT_GOALS_SET where user_id='40001001';
  execute immediate 'select mc, sum(ppln_wartosc) plan from prod_nonlife.mis_report_plans 
  where report_id = (select to_number(value) from prod_nonlife.view_parameters where view_name=''MIS'' and parameter_name=''MAX_REPORT_ID'')
    and year=2017 
    and month between 7 and 9 
    and ppln_jsta_symbol in (:subsidiary)
    and dcs_group in (:lob)
    and kanal in (:channel)
  group by month order by month' bulk collect into BULK_COLLECTOR
  using p_sub,p_lob,p_ch;
  forall x in BULK_COLLECTOR.first..BULK_COLLECTOR.last insert into ASYSTENT_TEST values BULK_COLLECTOR(x);
end;

Так что теперь, когда в столбце таблицы ASYSTENT_GOALS_SET SUBSIDIARY (varchar) содержится строка 12_00_00 (которая является кодом одного из дочерних), все работает нормально. Но проблема в том, что пользователь работает в двух дочерних компаниях, скажем, 12_00_00 и 13_00_00. Я понятия не имею, как записать это. Если столбец SUBSIDIARY состоит из: "12_00_00","13_00_00" или "12_00_00","13_00_00" или, возможно, 12_00_00 "," 13_00_00, я пробовал множество вариантов после поиска по темам, таким как "Удаление с одним / выходом / двойным qoutes". Может быть, я должен что-то изменить в немедленном исполнении?

Или, может быть, мой подход к этому вопросу совершенно неверен с самого начала (надеюсь, нет:)). Буду благодарен за поддержку.

2 ответа

Решение

Я не создавал описанную здесь табличную функцию, но эта статья вдохновила меня вернуться, чтобы попробовать regexp_substr функционировать снова.
Я изменился:
ppln_jsta_symbol in (:subsidiary)
в
ppln_jsta_symbol in (select regexp_substr((select subsidiary from ASYSTENT_GOALS_SET where user_id=''fake_num''),''[^,]+'', 1, level) from dual connect by regexp_substr((select subsidiary from ASYSTENT_GOALS_SET where user_id=''fake_num''), ''[^,]+'', 1, level) is not null)
Теперь это работает как шарм! Большое спасибо @Dessma за потраченное время и предложение!

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

Это кажется ошибочным требованием. Не беспокойтесь о количестве строк: базы данных оптимизированы для хранения и извлечения строк.

Что они не умеют делать, так это иметь дело с "многозначными" столбцами. Как показывает ваше собственное решение, оно не очень хорошее, оно очень далеко от хорошего, на самом деле это полная боль в шее. Отныне каждый раз, когда кому-то нужно работать с subsidiary им придется вызывать функцию. Добавить, изменить или удалить дочернюю компанию гораздо сложнее, чем следовало бы. Также нет возможности обеспечить целостность данных, т. Е. Проверить, что дочерняя компания действительна в отношении справочной таблицы.

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

Правильным решением, лучшим в отрасли на протяжении почти сорока лет, было бы признание того, что ВСПОМОГАТЕЛЬНЫЙ существует с гранулярностью, отличной от CHANNEL, и поэтому должен храниться в отдельной таблице.

Другие вопросы по тегам