How to pivot/merge rows based on condition in BigQuery? - sql

I have a table that looks like this:
record
name1
name2
to_merge
value1
value2
1
STEVE
null
false
30
null
2
JOHN
null
true
43
null
3
null
LAURA
true
null
66
4
JEN
null
false
18
null
I want this to be the output:
record
name1
name2
value1
value2
1
STEVE
null
30
null
2
JOHN
LAURA
43
66
3
JEN
null
18
null
This means I want to merge the rows with a TRUE value in the to_merge field. Any help is much appreciated!

Consider below
select * except(to_merge)
from your_table
where not to_merge
union all
select max(name1), max(name2),
max(value1), max(value2)
from your_table
where to_merge
if applied to data in your question - output is

Related

how can extract one row having not null values from a few of rows

for example
tableA has
id
condition_A
condition_B
condition_C
condition_D
AA
NULL
NULL
10
NULL
AA
15
NULL
NULL
NULL
AA
NULL
NULL
10
5
AA
NULL
20
NULL
NULL
AA
NULL
20
NULL
5
every condition has same value with same id
then i want to extract result like
id
condition_A
condition_B
condition_C
condition_D
AA
15
20
10
5
how can extract without null and only one rows?
Thank you :)
select max(condition_A), max(condition_B), max(Condition_C), max(Condition_D)
from tableA where id = 'AA'

Select Data as per the given output

Table 1:
ID
CALLID
CALLSTATUS
1
123
Generated
2
321
Not Generated
3
343
Generated
4
567
Not Generated
5
789
Generated
Table 2:
UID
ID
CALLID
GENERATEDATE
RESULT
11
1
123
2021/3/18
1
21
1
123
2021/4/20
1
31
1
123
2021/5/20
0
41
2
321
NULL
NULL
51
3
343
2021/4/21
1
61
4
567
NULL
NULL
71
5
789
2021/5/1
0
Output of Oracle should be like below table:
ID
CALLID
GENERATEDATE
CALLSTATUS
RESULT
1
123
2021/4/20
Generated
1
2
321
NULL
Not Generated
NULL
3
343
2021/4/21
Generated
1
4
567
NULL
Not Generated
NULL
5
789
2021/5/1
Generated
0
The output which I want should be like above table. For CALLID '123', as per table 2 last generated call is on '2021/5/20' but it's result is '0' which i don't want to select. It should select '2021/4/21' because it's result is '1'. But for CALLID '789', No RESULT is '1' so it should select Generated Date as '2021/5/1'.
You can use conditional aggregation along with NVL() function depending on the values for the result column such as
SELECT t1.id, MAX(t1.callid) AS callid,
NVL(MAX(CASE WHEN result = 1 THEN t2.generatedate END),
MAX(CASE WHEN NVL(result,0)!=1 THEN t2.generatedate END)) AS generateddate,
MAX(t1.callstatus) AS callstatus, MAX(result) AS result
FROM Table1 t1
JOIN Table2 t2
ON t2.id = t1.id
AND t2.callid = t1.callid
GROUP BY t1.id
ORDER BY t1.id
ID
CALLID
GENERATEDDATE
CALLSTATUS
RESULT
1
123
20/04/2021
Generated
1
2
321
Not Generated
3
343
21/04/2021
Generated
1
4
567
Not Generated
5
789
01/05/2021
Generated
0
Demo

Oracle query: if column A is null then condition on column B

I have a table
num1 num2 info1 info2 status1 status2 flag
14 11111 affsd sdf 10 - 1
135 22222 fds - 20 10 0
1513 33333 - fds 10 30 1
21 44444 dd a - 20 1
- 55555 ddwd - 10 - 0
Goal: to find most fitting record based on parameters and return flag.
Conditions:
if num is not null then match status1 to num1 and status2 to num2. If either of status is null then treat this null as "Match". i both are null then return f.e. 2;
if num is null:
match info1 to my_param_1 and info2 to my_param_2. status1 and status2 - if they exists in table then have to match to params, if they don't exists - they are null and they match.
if info1 and info2 is null then return f.e. 2
My actual solution is list of if-else and diffrent select in every if section, but now i wonder if this could be done in single query? Like when this column is null then condition on another. I tried something like
WHERE case when ... then...
but no luck.
I hope i explained right and everything is understood :)
Thanks!

Group multiple rows together

I have a table which contains the following and I am looking to group them to get the below output. Is it possible?
Input
ID Value1 Value2 Value3
5 Y NULL NULL
5 NULL 1 NULL
5 NULL NULL USA
5 NULL NULL NULL
6 N NULL NULL
6 NULL 2 NULL
6 NULL NULL GBP
6 NULL NULL NULL
Output
ID Value1 Value2 Value3
5 Y 1 USA
6 N 2 GBP
Group by the id and use max() to get the non-null value per each group
select id,
max(value1) as value1,
max(value2) as value2,
max(value3) as value3
from your_table
group by id
BTW you should think about changing you table design. It is not normalized.

Optimize rows to columns conversion

I have a big Oracle table (around 40 million rows) that looks like this:
ID Name Question Answer Reason
3 Name1 1 Yes blah blah
3 Name1 2 No NA
3 Name1 3 No NA
3 Name1 4 Yes blah2
3 Name1 5 Yes null
3 Name1 6 Yes blah3
3 Name1 7 No null
6 Name2 1 Yes blah4444
6 Name2 2 No null
6 Name2 3 Yes blah3
6 Name2 4 NA blah5
6 Name2 5 Yes null
6 Name2 6 Yes blah6
6 Name2 7 NA null
I need one row per ID i.e. I will need to add columns for each question's answer (there are 7 questions per ID) and each question's reason. I need to make it look like this:
ID Name Q1 Q1-Reason Q2 Q2-Reason Q3 Q3-Reason etc.
3 Name1 Yes blah blah No null
6 Name2 Yes blah4444 No null
My query currently looks like this:
select
A.ID,A.NAME,B1.Q1,B1.Q1-REASON,B2.Q2,B2.Q2-REASON
from
TABLENAME A
inner join
(
select distinct C1.ID,C1.ANSWER as Q1,C1.REASON as Q1-REASON
from TABLENAME C1
where C1.QUESTION=1
) B1 on B1.ID=A.ID
inner join
(
select distinct C2.ID,C2.ANSWER as Q2,C2.REASON as Q2-REASON
from TABLENAME C2
where C2.QUESTION=2
) B2 on B2.ID=A.ID
...
...
However, as the table is huge, this is taking a VERY long time to retrieve the data. Could someone suggest ways to optimize this query?
I'm on Oracle 10g and SQLDeveloper 4.0.2.15
You could do this:
SELECT
TABLENAME.ID,
TABLENAME.Name,
MAX(CASE WHEN TABLENAME.Question=1 THEN TABLENAME.Answer ELSE NULL END) AS Q1,
MAX(CASE WHEN TABLENAME.Question=1 THEN TABLENAME.Reason ELSE NULL END) AS Q1_Reason,
MAX(CASE WHEN TABLENAME.Question=2 THEN TABLENAME.Answer ELSE NULL END) AS Q2,
MAX(CASE WHEN TABLENAME.Question=2 THEN TABLENAME.Reason ELSE NULL END) AS Q2_Reason,
MAX(CASE WHEN TABLENAME.Question=3 THEN TABLENAME.Answer ELSE NULL END) AS Q3,
MAX(CASE WHEN TABLENAME.Question=3 THEN TABLENAME.Reason ELSE NULL END) AS Q3_Reason
/*And so on*/
FROM
TABLENAME
GROUP BY
TABLENAME.ID,
TABLENAME.Name