Avatar billede olf Nybegynder
29. juni 2007 - 20:07 Der er 8 kommentarer og
1 løsning

Stored procedure med liste af id'er

Hejsa,

Jeg vil frygteligt gerne lave en stored procedure der ligner nedenstående:

-----
CREATE OR REPLACE procedure test(p_ids IN arrayOfNumbers, p_cursor OUT sys_refcursor)

is
begin
    open p_cursor for
   
    select sex from brugerstamdata
    where brugerid in (p_ids);
end;
-----


Idéen er at jeg skal sende en liste af id'er ind med p_ids som så skal returneres.

Jeg er godt klar over at "p_ids IN arrayOfNumbers" som parameter ikke virker - det er det jeg gerne vil have hjælp til ;-)

Kan det lade sig gøre eller skal det laves på en helt anden måde? (og i så fald - nogen der har en idé til hvordan?)

PS: Det er en Oracle db ver. 10 der bruges.

/Ole
Avatar billede kalp Novice
29. juni 2007 - 20:09 #1
Du skal sende id'erne ind komma separeret.

så kan du lave en  - where id in (denkommasepareredeliste)
Avatar billede olf Nybegynder
29. juni 2007 - 20:19 #2
tak for hurtig kommentar!

Jeg har prøvet at lade p_ids være af type varchar2 og så lade værdien være "1,4,5". Det fejler (fordi der reelt kommer til at stå: where brugerid in ('1,4,5'); i stedet for: where brugerid in (1,4,5)).

Ligeledes har jeg nu prøvet at lade p_ids være af typen number og så lave en int array (i C#). Denne kunne dog ikke overføres som parameter...
Avatar billede kalp Novice
29. juni 2007 - 20:46 #3
har siddet og tænkt lidt - uden desværre lige og kunne komme på en god idé.
muligvis skal du sende det som en parameter af gangen og loope igennem dit array fra det programmeringssprog du anvender (hvis du da programmere i noget)
Avatar billede olf Nybegynder
29. juni 2007 - 20:52 #4
Det var desværre også den eneste tanke jeg selv lige kunne komme på. Så det gør jeg.

Tusind tak for forsøget. Det er altid rart med en andens mening (selvom begge naturligvis kan tage fejl :-)).

Du må gerne lægge et svar - ingen mulig løsning på et problem er også en løsning i min verden!
Avatar billede kalp Novice
29. juni 2007 - 20:57 #5
En løsning er det i hvertfald:)
men det kunne selvfølgelig være interessant hvordan man ellers kunne får en Stored Procedure til, at håndtere det selv:)

Der er ikke noget som hedder int[] array i Oracle :P men man kan vidst definere sine egne objekter, men hvordan det lige virker har jeg ikke beskæftiget mig med:)
Avatar billede Slettet bruger
29. juni 2007 - 22:52 #6
olf -> Måske kan du bruge det følgende eksempel. Det går ud på at oprette en global type som man derefter kan bruge.

create or replace type id_table_type is table of number
/
> type id_table_type Compiled.


insert into brugerstamdata values ( 1, 'M');
insert into brugerstamdata values (11, 'M');
insert into brugerstamdata values ( 2, 'M');
insert into brugerstamdata values (22, 'F');
insert into brugerstamdata values ( 3, 'F');
insert into brugerstamdata values (33, 'F');
> rows inserted

CREATE OR REPLACE
procedure demo(p_ids IN id_table_type, p_cursor OUT sys_refcursor)
is
begin
    open p_cursor for
    select *
      from brugerstamdata
    where brugerid in (select * from table(p_ids));
end;
/
> procedure Compiled.

declare
  v_cursor sys_refcursor;
  r        brugerstamdata%rowtype;
begin
  demo (
      id_table_type(11,22,33), v_cursor );
  loop
    fetch v_cursor into r;
    exit when v_cursor%notfound;
    dbms_output.put_line ('brugerid ' || r.brugerid || ' er en ' || r.sex);
  end loop;
end;
/

anonymous block completed
brugerid 11 er en M
brugerid 22 er en F
brugerid 33 er en F
Avatar billede olf Nybegynder
01. juli 2007 - 00:52 #7
Hej joern_h,

Tak for dit bud! Jeg indrømmer at jeg ikke er en haj i Oracle (har kun brugt det en måneds tid...) så det er mere end tænkeligt at jeg tager fejl her. Men som jeg ser det har jeg stadig en udfordring med at få data ind i der, hvor du kalder "demo(id_table_type(11,22,33), v_cursor );"... Men det er måske den del jeg så bare skal lave fra C#. For jeg er ikke helt klar over hvordan jeg her skal definere at det er af type id_table_type. Nå, men det må komme an på en prøve.

Tak for budet i hvert fald!

/Ole
Avatar billede Slettet bruger
02. juli 2007 - 08:40 #8
olf -> "demo(id_table_type(11,22,33), v_cursor)" er et procedurekald.

Argumenterne til proceduren er en in-parameter og en out-parameter. In-parameter er en tabel af numbers og out-parameter er en cursor.

In-parameter oprettes ved at kalde en konstruktor på id_table_type. Denne konstruktor kan tage et vilkårligt antal parametre.

Jeg læser dit problem som: "Jeg står med en kommasepareret streng af tal som jeg skal have konverteret til en tabel, før jeg kan komme videre." Hvis det er rigtigt, kan du måske bruge Paweł Baruts indlæg i Tom Kytes blog http://tkyte.blogspot.com/2006/06/varying-in-lists.html.

Det kan vel oversættes til

select items.extract('/l/text()').getStringVal() item
from table(xmlSequence(
extract(XMLType('<all><l>'||
replace('1,2,3',',','</l><l>')||'</l></all>')
,'/all/l'))) items;
Avatar billede olf Nybegynder
02. juli 2007 - 11:18 #9
Ah! Nu kan jeg forstå det! Uden dog at have prøvet det af, ser det ud til at ville virke (nu har jeg løst problemet på anden vis). Men du skal da stadig belønnes for det!

Så hvis du lægger et svar på spørgsmål http://www.eksperten.dk/spm/785872 får du point (og tusind tak for hjælpen!)

/Ole
Avatar billede Ny bruger Nybegynder

Din løsning...

Tilladte BB-code-tags: [b]fed[/b] [i]kursiv[/i] [u]understreget[/u] Web- og emailadresser omdannes automatisk til links. Der sættes "nofollow" på alle links.

Loading billede Opret Preview
Kategori
Computerworld tilbyder specialiserede kurser i database-management

Log ind eller opret profil

Hov!

For at kunne deltage på Computerworld Eksperten skal du være logget ind.

Det er heldigvis nemt at oprette en bruger: Det tager to minutter og du kan vælge at bruge enten e-mail, Facebook eller Google som login.

Du kan også logge ind via nedenstående tjenester