Search code examples
sqloracleplsql

How to select the unique values in one column and group by a different column


I have a table in Oracle that has a schema as shown below

I want to get the output as shown in the result section. Any idea what the WHERE clause should look like in Oracle to get the output I need?

Table

col1_string_primary_key col2_number   col3_string              col4_timestamp
-----------------------------------------------------------------------------
                  11-11           1          str1         2024/09/04 00:00:00
                  22-22           2          str2         2024/09/04 00:01:00
                  33-33           1          str1         2024/09/04 00:02:00
                  44-44           4          str4         2024/09/04 00:03:00
                  55-55           1          str7         2024/09/04 00:04:00
                  44-44           2          str3         2024/09/04 00:04:00
                  55-55           1          str1         2024/09/04 00:00:01

Desired Query?

select 
  col2_number, col3_string
from 
  table
where 
      col4_timestamp >= to_timestamp('2024-09-04 00:00:00', 'YYYY-MM-DD HH24:MI:SS') 
  AND col4_timestamp  < to_timestamp('2024-09-04 00:05:00', 'YYYY-MM-DD HH24:MI:SS')

Desired Result

col2_number col3_string
-----------------------
          1   str1,str3
          2        str2
          4        str4

Solution

  • That looks like a listagg function problem, but ... desired result doesn't really match sample data because

    • I didn't quite get what you want simply by looking at info you posted (where clause doesn't filter anything, it returns all rows you posted), or
    • you forgot to actually explain rules which lead from source to target

    Anyway, here's an option you might be interested in, see if it helps.

    Sample data:

    SQL> with test (pk, col2, col3, col4) as
      2    (select '11-11', 1, 'str1', to_date('2024/09/04 00:00', 'yyyy/mm/dd hh24:Mi') from dual union all
      3     select '22-22', 2, 'str2', to_date('2024/09/04 00:01', 'yyyy/mm/dd hh24:mi') from dual union all
      4     select '33-33', 1, 'str2', to_date('2024/09/04 00:02', 'yyyy/mm/dd hh24:mi') from dual union all
      5     select '44-44', 4, 'str4', to_date('2024/09/04 00:03', 'yyyy/mm/dd hh24:mi') from dual union all
      6     select '55-55', 1, 'str7', to_date('2024/09/04 00:04', 'yyyy/mm/dd hh24:mi') from dual union all
      7     select '44-44', 2, 'str3', to_date('2024/09/04 00:04', 'yyyy/mm/dd hh24:mi') from dual union all
      8     select '55-55', 1, 'str1', to_date('2024/09/04 00:01', 'yyyy/mm/dd hh24:mi') from dual
      9    )
    

    Query begins here:

     10  select col2, listagg(distinct col3, ', ') within group (order by col3) col3
     11  from test
     12  where col4 >= to_date('2024/09/04 00:00', 'yyyy/mm/dd hh24:mi')
     13    and col4 <  to_date('2024/09/04 00:05', 'yyyy/mm/dd hh24:mi')
     14  group by col2;
    
          COL2 COL3
    ---------- --------------------
             1 str1, str2, str7
             2 str2, str3
             4 str4
    
    SQL>