SQL Query to achieve the sequence in the below format - sql

I am trying to find solution to achieve the result in the below format using sql.
I have two columns:
col1 col2
1 e
1 e
1 e
2 e2
2 e2
2 e2
3 e3
3 e3
4 e4
4 e4
4 e4
4 e4
4 e4
4 e4
6 e6
6 e6
6 e6
where col1 has the sequence number and col2 has the events where the col1 has the numbers starting from 1 to 10 ...and so on for each batch of events i.e first batch has the sequence 1, next 2 assigned and so on.
I am trying to renumber the sequence col1 in the format below using sql
col1 col2
1 e
2 e
3 e
1 e2
2 e2
3 e2
1 e3
2 e3
1 e4
2 e4
3 e4
4 e4
5 e4
6 e4
1 e6
2 e6
3 e6

Maybe you want this:
SELECT
ROW_NUMBER() OVER (PARTITION BY col2 ORDER BY col2) col1,
col2
FROM
table_name
ORDER BY
col2;

Try this:
SELECT col1, col2 FROM YourTable ORDER BY col2, col1
ORDER BY clause helps to get the result in order.

Check Col2 in your procedure use logic Like:
IF col2='e' Then
Begin
RESET SEQUENCE
SEQUENCE
end
else IF col2='p' Then
Begin
RESET SEQUENCE
SEQUENCE
end

Related

Getting exception while executing the query to compare two values

While executing a query to compare the rates of two columns and display if one is grater than other I am getting ORA-01427 exception
Here is the data set. This is mocked up data . Data size is huge in databse
Table1
col1 col2 col3 col4 col5 col6
c1 c1test 85 85 I 5
c2 c2test 85 85 I 3
c3 c3test 85 85 E 6
c4 c4test G1 G1 E 7
c5 c5test G1 G1 E 5
c6 c6test G1 G1 E 8
c7 c7test G1 G1 I 3
c8 c8test G1 G1 G 7
Table2
col1 col2 col3 col4 col5
85 85 D I 3
85 85 D E 5
G1 G1 D E 5
G1 G1 D I 3
G1 G1 D G 5
G1 G1 E I 2
G1 G1 E E 2
85 85 E I 3
Expected result
We need to compare the value of col5 of table2 with the col6 of table1 to find out the values greater in col6 of table1 and display the records. Comparison needs to be done only for col3 equals D values.
col1 col2 col3 col4 col5 col6
c1 c1test 81 81 I 5
c3 c3test 81 81 E 6
c4 c4test G1 G1 E 7
c6 c6test G1 G1 E 8
c8 c8test G1 G1 G 7
I am using the below query
Select * from table1 where
col6 > (select col5 from
table2 where col3='D'
and col1=table1.col3
and col2=table1.col4
and col4=table1.col5
This throws an ora-01427 exception. Can you pls hel to get the expected output.
If you are looking for value grater than any value of table2.col5, try this
SELECT t1.*
FROM table1 t1
WHERE t1.col6 > ANY (SELECT t2.col5
FROM table2 t2
WHERE t2.col3 = 'D'
AND t2.col1 = t1.col3
AND t2.col2 = t1.col4
AND t2.col4 = t1.col5
);
If you need table1.col6 should be greater than all values found in table2.col5 use ALL instead of ANY
Your subquery is returning multiple rows. You can use min() or max() to get around this. I'm not sure which logic you really want:
Select t1.*
from table1 t1
where t1.col6 > (select max(t2.col5)
from table2 t2
where t2.col3 = 'D' and
t2.col1 = t1..col3 and
t2.col2 = t1.col4 and
t2.col4 = t1.col5
);

Remove duplicate values from string in oracle

I have requirement where I have input data like
Col1 COl2 Col3
A1 2 B
A1 1 A
A1 3 B
B1 1 A
B2 2 B
B2 3 C
B4 4 C
B5 5 A
B6 6 B
Output Required:
Col1 COl2 Col3
A1 2 AB
A1 1 AB
A1 3 AB
B1 1 ABC
B2 2 ABC
B2 3 ABC
B4 4 ABC
B5 5 ABC
B6 6 ABC
Solution Tried:
select col1,col2,listagg(col3,'') within group (order by col3) over(partition by col1)
from tab
Output of the query:
Col1 COl2 Col3
A1 2 ABB
A1 1 ABB
A1 3 ABB
B1 1 AABBCC
B2 2 AABBCC
B2 3 AABBCC
B4 4 AABBCC
B5 5 AABBCC
B6 6 AABBCC
Can someone help here in removing repeating alphabets.
Thanks
You can use a subquery:
select col1, col2,
listagg(case when seqnum = 1 then col3 end, '') within group (order by col3) over (partition by col1)
from (select t.*,
row_number() over (partition by col1, col3 order by col3) as seqnum
from tab t
) t

How to group specific SQL columns and retrieve rows with highest counts for those columns? [duplicate]

This question already has answers here:
How to select the first row of each group?
(9 answers)
Closed 1 year ago.
I have the following data:
col_1 | col_2 | col_3 | col_4
-----------------------------
a1 b1 c1 d1
a1 b2 c1 d1
a1 b3 c1 d1
a1 b4 c1 d2
a1 b5 c2 d2
a1 b6 c2 d2
a1 b7 c1 d3
a1 b8 c2 d3
a1 b9 c3 d3
a1 b10 c1 d2
a1 b11 c2 d3
a2 b12 c1 d1
a3 b13 c1 d1
I am interested in being able to:
Return rows where the value for col_1 is unique
For each row in the result, it should return the values for the columnns that have the highest counts when grouping by: col_3, col_4
For example, I would like the output to return the following:
col_1 | col_2 | col_3 | col_4
-----------------------------
a1 b1 c1 d1
a2 b12 c1 d1
a3 b13 c1 d1
Notice in the result that each value in col_1 is unique. Also note that for a1, it returned with c1 and d1 as they had the highest group by counts for a1.
How can I achieve this by SQL query? I will be using it for a Hive SQL query.
With row_number() window function:
select t.col_1, t.col_2, t.col_3, t.col_4
from (
select col_1, min(col_2) col_2, col_3, col_4,
row_number() over (partition by col_1 order by count(*) desc) rn
from tablename
group by col_1, col_3, col_4
) t
where t.rn = 1
See the demo.
Results:
| col_1 | col_2 | col_3 | col_4 |
| ----- | ----- | ----- | ----- |
| a1 | b1 | c1 | d1 |
| a2 | b12 | c1 | d1 |
| a3 | b13 | c1 | d1 |
You can use aggregation and window functions:
select col_1, col_2, col_3, col_4
from (
select
col_1,
col_2,
col_3,
col_4,
rank() over(partition by col_1 order by count(*) desc) rn
from mytable t
group by col_1, col_2, col_3, col_4
) t
where rn = 1
You can use window functions if you want the complete rows:
select t.*
from (select t.*,
rank() over (partition by col1 order by cnt desc) as seqnum
from (select t.*, count(*) over (partition by col1, col3, col4) as cnt
from t
) t
) t
where seqnum = 1;
The innermost subquery counts the number of rows for each col1/col3/col4 combination. The middle subquery enumerates the rows the highest count for each col1. The outermost filters for the highest count.

SQL interview questions

Table-1
Col1 col2
11 A
26 B
31 C
43 D
Table-2
Col1 col2
16 E
46 F
39 G
42 H
And need output is
Col1 col2 Col1 col2
11 A 16 E
26 B 46 F
31 C 39 G
43 D 42 H
Here's one option:
SQL> with
2 -- sample data
3 a (col1, col2) as
4 (select 11, 'A' from dual union all
5 select 26, 'B' from dual union all
6 select 31, 'C' from dual union all
7 select 43, 'D' from dual
8 ),
9 b (col1, col2) as
10 (select 16, 'E' from dual union all
11 select 46, 'F' from dual union all
12 select 39, 'G' from dual union all
13 select 42, 'H' from dual
14 ),
15 -- find something to join rows on - for example, row number. Your example shows that
16 -- values are sorted by COL2
17 a2 as
18 (select col1, col2, row_number() over (order by col2) rn from a),
19 b2 as
20 (select col1, col2, row_number() over (order by col2) rn from b)
21 -- join a2 and b2 on RN
22 select a2.col1, a2.col2, b2.col1, b2.col2
23 from a2 join b2 on a2.rn = b2.rn
24 order by a2.col1;
COL1 COL2 COL1 COL2
----- ---- ----- ----
11 A 16 E
26 B 46 F
31 C 39 G
43 D 42 H
SQL>
select t1.col1, t1.col2, t2.col1, t2.col2 from table1 as t1
left join table2 as t2 on 1=1
Try this
select * from table1 t1 join table2 t2 on ascii(t1.col2)+4 = ascii(t2.col2);
Note: this only works with the specific input provided, but why not? It just goes to show that providing minimal input and expected output is not sufficient. You have to explain what rules the input should follow and what rules the processing should follow.
Littlefoot answers a different question than I do, but even he silently makes some assumptions. For example, he decided not to show any output if there are unmatched rows on one side or the other.
The correct real-world answer to this interview question would be to list the questions one would have to ask before being able to supply an appropriate answer.

Simplest way to repeat every N rows in sql

I know this is possible through some complex techniques, i want to know any simplest way to achieve this patter that every 10 rows should repeat .
for example
select a,b from tablename; (repeating 2 for example)
will give
a1,b1
a2,b2
a1,b1
a2.b2
a3,b3
a4,b4
a3,b3
a4,b4
where if it was 10 it will go like
a1,b1 to a10,b10 again a1,b1 to a10,b10
then
a11,b11 to a20,b20 again a11,b11 to a20,b20
and so on
You want blocks of ten rows repeated twice. So to get:
rows 1 to 10
rows 1 to 10
rows 11 to 20
rows 11 to 20
...
In order to get rows n-fold cross join with a table holding n records. (You get such for instance by querying a big enough table and stop at rowcount n.)
You also need the row number of your original records, so you can get block 1 first, then block 2 and so on. Use integer division to get from row numbers to blocks.
select t.a, t.b
from (select a, b, row_number() over (order by a, b) as rn from tablename) t
cross join (select rownum as repeatno from bigenoughtable where rownum <= 2) r
order by trunc((t.rn -1) / 10), r.repeatno, t.a, t.b;
Use a CTE and union all:
with rows as (
select a, b
from tablename
where rownum <= 2
)
select *
from rows
union all
select *
from rows;
Just some caveats to this. You should use an order by if you want particular rows from the table. This is important, because the same select can return different sets of rows. Actually, considering this, a better way is probably:
with rows as (
select a, b
from tablename
where rownum <= 2
)
select *
from rows cross join
(select 1 as n from dual union all select 2 from dual) n;
I would rather not use UNION so many times. My way would be CONNECT BY ROWNUM <=N. Actually a CARTESIAN JOIN. So, basically you need a ROW GENERATOR to cartesian join with it.,
Update
For example, this will repeat 10 rows 2 times -
SQL> WITH t AS
2 ( SELECT 'a1' A, 'b1' b FROM dual
3 UNION ALL
4 SELECT 'a2' a, 'b2' b FROM dual
5 UNION ALL
6 SELECT 'a3' a, 'b3' b FROM dual
7 UNION ALL
8 SELECT 'a4' A, 'b4' b FROM dual
9 UNION ALL
10 SELECT 'a5' A, 'b5' b FROM dual
11 UNION ALL
12 SELECT 'a6' a, 'b6' b FROM dual
13 UNION ALL
14 SELECT 'a7' A, 'b7' b FROM dual
15 UNION ALL
16 SELECT 'a8' a, 'b8' b FROM dual
17 UNION ALL
18 SELECT 'a9' a, 'b9' b FROM dual
19 UNION ALL
20 SELECT 'a10' a, 'b10' b FROM dual
21 )
22 SELECT A,B FROM t,
23 (SELECT 1 FROM DUAL CONNECT BY ROWNUM <=2
24 )
25 /
A B
--- ---
a1 b1
a2 b2
a3 b3
a4 b4
a5 b5
a6 b6
a7 b7
a8 b8
a9 b9
a10 b10
a1 b1
a2 b2
a3 b3
a4 b4
a5 b5
a6 b6
a7 b7
a8 b8
a9 b9
a10 b10
20 rows selected.
SQL>
So, above CONNECT BY ROWNUM <=10 means repeat the rows 10 times. If you want it to be repeated N times use CONNECT BY ROWNUM <=N.