-1
SELECT DISTINCT L.* FROM LABALES L , MATCHES M 
WHERE M.LIST LIKE '%ENG' 
ORDER BY L.ID

I need to create function with this select, I tried this but it doesn't work.

CREATE OR REPLACE FUNCTION getSoccerLists
RETURN varchar2  IS 
list varchar2(2000);
BEGIN
   SELECT DISTINCT L.* FROM LABALES L , MATCHES M 
   WHERE M.LIST LIKE '%ENG' 
   ORDER BY L.ID
   return list;
END;

How will I create function that returns all from table L.

Thanks

Nishant Gupta
  • 3,533
  • 1
  • 11
  • 18
civesuas_sine
  • 119
  • 2
  • 15
  • No join conditions? That query doesn't make much sense... – jarlh Apr 06 '18 at 10:16
  • What error it is giving?? – Nishant Gupta Apr 06 '18 at 10:20
  • @jarlh When i run select i get results so select is good. But i want it in function.. – civesuas_sine Apr 06 '18 at 10:30
  • @NishantGupta sql statment ignored, end of line of qouted identifer ,missing double qoute – civesuas_sine Apr 06 '18 at 10:31
  • sorry,but the follwong link is not from SO but will definetly help you to solve your problem- https://sqljana.wordpress.com/2017/01/22/oracle-return-select-statement-results-like-sql-server-sps-using-pipelined-functions/ – Kedar Limaye Apr 06 '18 at 10:37
  • Why do you want a function in the first place? If you just want to store the query for reuse, then make it a view. And as has been mentioned: The query makes no sense. You duplicate LABALES records by the number of '%ENG' MATCHES and then you dismiss all duplicates again with `DISTINCT`. You'll probably get the same result with a mere `select * from labales`. – Thorsten Kettner Apr 06 '18 at 12:11
  • I been told to make function or procedure instead of query, probably not to run select all the time when someone needs this results. This is the select i want in function {SELECT DISTINCT L.* FROM SOCCER_PREMATCH_LISTS L , SOCCER_PREMATCH_MATCHES M WHERE M.LIST LIKE '%' || (L.SUB_LIST) || '%' AND (TO_TIMESTAMP((M.M_DATE || ' ' || M.M_TIME), 'DD.MM.YYYY HH24:MI') > (SELECT SYSTIMESTAMP AT TIME ZONE 'CET' FROM DUAL)) ORDER BY L.ID; } – civesuas_sine Apr 06 '18 at 12:17
  • @civesuas_sine If your problem is resolved by any of the solution shared below, please accept it and close the question for future readers of your post, You gain reputations too. Read this to undersatnd how SO works https://stackoverflow.com/help/someone-answers – XING Apr 11 '18 at 08:45

3 Answers3

1

You may use implicit result using DBMS_SQL.RETURN_RESULT(Oracle12c and above) in a procedure using a cursor to your query.

CREATE OR REPLACE PROCEDURE getSoccerLists 
AS
x SYS_REFCURSOR;
BEGIN
  OPEN x FOR SELECT DISTINCT L.* FROM LABALES L 
   JOIN  MATCHES M  ON ( 1=1 ) -- join condition
       WHERE M.LIST LIKE '%ENG' 
       ORDER BY L.ID; 
   DBMS_SQL.RETURN_RESULT(x);
END;
/

then simply call the procedure

EXEC getSoccerLists;

For lower versions(Oracle 11g) , you may use a print command to display the cursor's o/p passing ref cursor as out parameter.

CREATE OR REPLACE PROCEDURE getSoccerLists (x OUT SYS_REFCURSOR) 
AS
BEGIN
  OPEN x FOR SELECT DISTINCT L.* FROM LABALES L 
   JOIN  MATCHES M  ON ( 1=1 ) -- join condition
       WHERE M.LIST LIKE '%ENG' 
       ORDER BY L.ID; 
END;
/

Then, in SQL* Plus or running as script in SQL developer and Toad, you may get the results using this.

VARIABLE r REFCURSOR;
EXEC  getSoccerLists (:r);

PRINT r;

Another option is to use TABLE function by defining a collection of the record type of the result within a package.

Refer Create an Oracle function that returns a table

Kaushik Nayak
  • 30,772
  • 5
  • 32
  • 45
0

I guess this questions is a repetition of the your previously asked question, where you wanted to get all the columns of tables but into separate column. I already answered in stating this you cannot do if you call your function via a SELECT statement. If you call your function in a Anoymous block you can display it in separate columns.

Here Oracle function returning all columns from tables

Alternatively, you can get the results separated by a comma(,) or pipe (|) as below:

CREATE OR REPLACE
  FUNCTION getSoccerLists
    RETURN VARCHAR2
  IS
    list VARCHAR2(2000);
  BEGIN
    SELECT col1
      ||','
      ||col2
      ||','
      ||col2
    INTO LIST
    FROM SOCCER_PREMATCH_LISTS L ,
      SOCCER_PREMATCH_MATCHES M
    WHERE M.LIST LIKE '%' || (L.SUB_LIST)  || '%'
    AND (TO_TIMESTAMP((M.M_DATE      || ' '      || M.M_TIME), 'DD.MM.YYYY HH24:MI') >
      (SELECT SYSTIMESTAMP AT TIME ZONE 'CET' FROM DUAL
      ))
    ORDER BY L.ID");
  Return list;
  End;

Note here if the column size increased 2000 chars then again you will lose the data.

Edit:

From your comments

I want it to return a table set of results.

You then need to create a table of varchar and then return it from the function. See below:

CREATE TYPE var IS  TABLE OF VARCHAR2(2000);
/

CREATE OR REPLACE
FUNCTION getSoccerLists
  RETURN var
IS
  --Initialization
  list VAR :=var();
BEGIN
  SELECT NSO ||',' ||NAME BULK COLLECT INTO LIST FROM TEST;
  RETURN list;
END;

Execution:

select * from table(getSoccerLists);

Note: Here in the function i have used a table called test and its column. You replace your table with its columnname.

Edit 2:

--Create a object with columns same as your select statement
CREATE   TYPE v_var IS  OBJECT
(
col1 NUMBER,
col2 VARCHAR2(10)
)
/
--Create a table of your object
CREATE OR REPLACE TYPE var IS TABLE OF v_var;
/

CREATE OR REPLACE FUNCTION getSoccerLists
  RETURN var
IS
  --Initialization
  list VAR :=var();
BEGIN
   --You above object should have same columns with same data type as you are selecting here 
  SELECT v_var( NSO ,NAME) BULK COLLECT INTO LIST FROM TEST;
  RETURN list;
END;

Execution:

select * from table(getSoccerLists);
XING
  • 9,608
  • 4
  • 22
  • 38
  • @civesuas_sine. You need to put your actual columns. I am not giving ready made code for you. It's just a demo to help out your issue. Just replace all the columns of your table separate it via a `,` or `|`. – XING Apr 06 '18 at 10:54
  • exact fetch returns more than requested number of rows – civesuas_sine Apr 06 '18 at 10:56
  • @civesuas_sine it means your query returns multiple rows on your filter clause. If this is the case then again either you need to make sure your query return a single row or you need to return a table of your resultset using either a `sys_refcursor` or by decalring a `object` – XING Apr 06 '18 at 10:59
  • ORA-00955: name is already used by an existing object , when I try to run statement – civesuas_sine Apr 06 '18 at 11:41
  • @civesuas_sine Not sure what and how you are executing. I showed you a working demo. Also as mentioned earlier, you cannot do as you showed in the pic. At max you can separate the results using `,` or `|` and display result in a single column since you are returning a table of varchar. Or you need to create a object of your table type and then use it. See edit2 – XING Apr 06 '18 at 11:57
0

This is not an answer on how to build a function for this, as I'd recommend to make this a view instead:

CREATE OR REPLACE VIEW view_soccer_list AS
  SELECT * 
  FROM soccer_prematch_lists l
  WHERE EXISTS
  (
    SELECT *
    FROM soccer_prematch_matches m 
    WHERE m.list LIKE '%' || (l.sub_list) || '%' 
      AND TO_TIMESTAMP((m.m_date || ' ' || m.m_time), 'DD.MM.YYYY HH24:MI') > 
            (SELECT SYSTIMESTAMP AT TIME ZONE 'CET' FROM DUAL)
  );

Then call it in a query:

SELECT * FROM view_soccer_list ORDER BY id;

(It makes no sense to put an ORDER BY clause in a view, because you access the view like a table, and table data is considered unordered, so you could not rely on that order. The same is true for a pipelined function youd access with FROM TABLE (getSoccerLists). Always put the ORDER BY clause in your final queries instead.)

Thorsten Kettner
  • 89,309
  • 7
  • 49
  • 73
  • @ThorstenKettnerDont need view, can you just create function using this select ? – civesuas_sine Apr 06 '18 at 14:19
  • Well, I just thought it makes no sense to have a function do the same thing. The only difference to a view is that it's slower. If you want to write a function anyway, you may want to look up pipelined functions: https://oracle-base.com/articles/misc/pipelined-table-functions – Thorsten Kettner Apr 06 '18 at 15:01