Создание функции агрегации в Oracle 10g, возвращающей бесполезную ошибку - PullRequest
3 голосов
/ 26 сентября 2011

Я получил некоторую помощь, и меня привели к этой странице и этому объяснению , которое должно содержать эффективный способ агрегирования вещей.

Он предлагаетиспользуйте функцию de COLLECT и некоторые другие пользовательские функции.Я пытаюсь справиться с этим, но сообщения об ошибках (плюс моя новизна) не самые полезные.

Функция:

CREATE OR REPLACE TYPE t_varchar2_tab AS TABLE OF VARCHAR2(4000);

CREATE OR REPLACE FUNCTION tab_to_string (
    p_varchar2_tab  IN  t_varchar2_tab, 
    p_delimiter     IN  VARCHAR2 DEFAULT ',')
RETURN VARCHAR2 IS
  l_string     VARCHAR2(32767);
BEGIN
  FOR i IN p_varchar2_tab.FIRST .. p_varchar2_tab.LAST LOOP
    IF i != p_varchar2_tab.FIRST THEN
      l_string := l_string || p_delimiter;
    END IF;
    l_string := l_string || p_varchar2_tab(i);
  END LOOP;
  RETURN l_string;
END tab_to_string;

И мои тесты:

with my_table as
(
    select 'user1' as usrid, 'ab' as prodcode from dual union
    select 'user1' as usrid, 'bb' as prodcode from dual union
    select 'user1' as usrid, 'a' as prodcode from dual union
    select 'user2' as usrid, 'db' as prodcode from dual union
    select 'user2' as usrid, 'b' as prodcode from dual union
    select 'user2' as usrid, 'bfdd' as prodcode from dual
)
select
    usrid, 
    tab_to_string(CAST(COLLECT(prodcode) AS t_varchar2_tab)) AS codes
from
    my_table
group by
    usrid

дал бы мне ORA-06553: PLS-306: wrong number or types of arguments in call to 'TAB_TO_STRING'

Это в значительной степени копирование и вставка из источника, который я упоминал в начале, и эта функция имеет для меня смысл ... чего мне не хватает?

спасибо!

[EDIT] Кодо решил, что одной из проблем было то, что Oracle понимал 'a' как char чем варчар .Это привело вопрос к реальной проблеме.Я обновил его, чтобы он был сфокусирован.

1 Ответ

2 голосов
/ 26 сентября 2011

По причинам, которые я не совсем понимаю, Oracle считает, что столбец PRODCODE вашей синтетической таблицы не является столбцом VARCHAR2.Если вы слегка измените одно из значений PRODCODE, оно будет работать:

with my_table as
(
    select 'user1' as usrid, 'ab' as prodcode from dual union
    select 'user1' as usrid, 'b' as prodcode from dual union
    select 'user1' as usrid, 'c' as prodcode from dual union
    select 'user2' as usrid, 'd' as prodcode from dual union
    select 'user2' as usrid, 'e' as prodcode from dual union
    select 'user2' as usrid, 'f' as prodcode from dual
)
select
    usrid, 
    tab_to_string(CAST(COLLECT(prodcode) AS t_varchar2_tab)) AS codes
from
    my_table
group by
    usrid
...