Convert one column to multiple columns in postgres - postgresql

I have a table like this below :
Would like to change the format as below on postgres :
I tried to use the case statement but did not give me desired results.
Thank you in advance for the help !
EDIT
select (case when column_1='A' then column_1 else 'other' end) column_1,
(case when column_1='B' then Column_1 else 'other' end) column_2 from test_t
where id= random_value;
Each time the query returns only 2 rows and the row values in the column_1 are dynamic and not fixed.

Here we go...
CREATE TABLE test_table(column_1 text);
INSERT INTO test_table ('A'),('B');
SELECT * FROM test_table ;
column_1
---------
B
A
SELECT
max(case when column_1='A' THEN column_1 END) column_1,
max(case when column_1='B' THEN column_1 END) column_2
from test_table;
column_1 | column_2
----------+----------
A | B
In PostgreSQL you can do this easily with crosstab(), but in greenplum still it is not implemented

Please refer to this link. Previously answered.
stackoverflow.com/a/10625294/1870151
SELECT
unnest(array['col1', 'col2', 'col3']) AS "Columns",
unnest(array[col1::text, col2::text, col3::text]) AS "Values"
FROM tbl;

You didn't really provide enough information to really answer the question but this is how you convert those two rows from one column into two columns and forced into a single row.
select max(column_1) as column_1, max(column_2) as column_2
from (select case when column_1 = 'A' then column_1 else '' end as column_1,
case when column_1 = 'B' then column_1 else '' end as column_2
from table_name);

If the result you want to transpose always has only 2 rows, this will work regardless of the contents of those columns, as you asked:
SELECT
MAX(CASE WHEN row_number=1 THEN column_1 END) column_1,
MAX(CASE WHEN row_number=2 THEN column_1 END) column_2
FROM (SELECT column_1,
ROW_NUMBER() OVER (ORDER BY test_table.column_1)
FROM test_table) t;
column_1 | column_2
----------+----------
A | B

Related

How to selecting subqueries correctly

I have two queries that give me back a single entry. How can I select both of these as on table?
query1: Select max([column3]) from [table1] => 42
query2: Select Top 1 [column1] from [table1] => 'test'
I want a resultset like this
result1
result2
42
'test'
But how to do it correctly? Can I maybe select from nowhere somehow?
You could use ROW_NUMBER, twice:
WITH cte AS (
SELECT *, ROW_NUMBER() OVER (ORDER BY column3 DESC) rn1,
ROW_NUMBER() OVER (ORDER BY some_col) rn2
FROM table1
)
SELECT MAX(CASE WHEN rn1 = 1 THEN column3 END) AS result1,
MAX(CASE WHEN rn2 = 1 THEN column1 END) AS result2
FROM cte;
Note that I assume there exists a column some_col which you intend to use for choosing the column1 value.

postgres how to insert values with 2 selects

I'm trying to do a query on Postgres but it's not working. I'd like to create an insert query with 2 select:
Example :
INSERT INTO table1 (id_1, id_2)
SELECT id from table_2 where code='01',
SELECT id from table_2 where code='02';
I don't find the good syntax for this.
I believe below query will works for your use case
INSERT INTO stats(totalProduct, totalCustomer, totalOrder)
VALUES(
(SELECT COUNT(*) FROM products),
(SELECT COUNT(*) FROM customers),
(SELECT COUNT(*) FROM orders)
);
you can changes query accordingly
You can add one more SELECT to achieve this
INSERT INTO table_1 (id_1, id_2)
SELECT
(SELECT id FROM table_2 WHERE code = '01') AS Id_1,
(SELECT id FROM table_2 WHERE code = '02') AS Id_2;
Or you may try with CASE expression:
INSERT INTO table1 (id_1, id_2)
SELECT MAX(CASE WHEN code = '01' THEN id ELSE 0 END) AS Id_1,
MAX(CASE WHEN code = '02' THEN id ELSE 0 END) AS Id_2
FROM table_2
Please refer to the working fiddle on db<>fiddle

Add column to SQL query

There is some select
SELECT column1,
COUNT(CASE column2 WHEN 'type1' THEN 1 ELSE NULL END) AS Type1Count,
COUNT(CASE column2 WHEN 'type2' THEN 1 ELSE NULL END) AS Type2Count,
COUNT(CASE column2 WHEN 'type3' THEN 1 ELSE NULL END) AS Type3Count
FROM Yourtable
GROUP BY column1
help me please, how i can add column0 which values corresponds to column1 in select query, some thing like that
SELECT column0, column1,
COUNT(CASE column2 WHEN 'type1' THEN 1 ELSE NULL END) AS Type1Count,
COUNT(CASE column2 WHEN 'type2' THEN 1 ELSE NULL END) AS Type2Count,
COUNT(CASE column2 WHEN 'type3' THEN 1 ELSE NULL END) AS Type3Count
FROM Yourtable
GROUP BY column1
but my variant is not work...
When you are selecting the exact value of some columns, and aggregating (e.g. COUNT(), SUM()) on others, you need to tell the database which is which in the GROUP BY clause.
If you say:
GROUP BY column0, column1
Then for every unique combination of column0 and column1, you will get an extra row of results, with the COUNT() expressions calculated across all the rows in the table for that combination.
If you only want one row for each distinct value of column1, you need to instead tell the database which value of column0 you are interested in. For instance, you might ask for the minimum value of column0 for each column1 with this:
SELECT MIN(column0), column1 ... GROUP BY column1
Which means:
I want one row for each distinct value of ... (GROUP BY ...)
... column1 (... column1)
For each row, show me (SELECT):
The minimum value of column0 in that group
The value of column1 which will be the same for everything in that group

postgresql where clause behavior

I made two queries that I thought should have the same result:
SELECT COUNT(*) FROM (
SELECT DISTINCT ON (id1) id1, value
FROM (
SELECT table1.id1, table2.value
FROM table1
JOIN table2 ON table1.id1=table2.id
WHERE table2.value = '1')
AS result1 ORDER BY id1)
AS result2;
SELECT COUNT(*) FROM (
SELECT DISTINCT ON (id1) id1, value
FROM (
SELECT table1.id1, table2.value
FROM table1
JOIN table2 ON table1.id1=table2.id
)
AS result1 ORDER BY id1)
AS result2
WHERE value = '1';
The only difference being that one had the WHERE clause inside SELECT DISTINCT ON, and the other outside that, but inside SELECT COUNT. But the results were not the same. I don't understand why the position of the WHERE clause should make a difference in this case. Can anyone explain? Or is there a better way to phrase this question?
here's a good way to look at this:
SELECT DISTINCT ON (id) id, value
FROM (select 1 as id, 1 as value
union
select 1 as id, 2 as value) a;
SELECT DISTINCT ON (id) id, value
FROM (select 1 as id, 1 as value
union
select 1 as id, 2 as value) a
WHERE value = 2;
The problem has to do with the unique conditions and what is visible where. It is behavior by design.

Aggregate GREATEST in T-SQL

My SQL is rusty -- I have a simple requirement to calculate the sum of the greater of two column values:
CREATE TABLE [dbo].[Test]
(
column1 int NOT NULL,
column2 int NOT NULL
);
insert into Test (column1, column2) values (2,3)
insert into Test (column1, column2) values (6,3)
insert into Test (column1, column2) values (4,6)
insert into Test (column1, column2) values (9,1)
insert into Test (column1, column2) values (5,8)
In the absence of the GREATEST function in SQL Server, I can get the larger of the two columns with this:
select column1, column2, (select max(c)
from (select column1 as c
union all
select column2) as cs) Greatest
from test
And I was hoping that I could simply sum them thus:
select sum((select max(c)
from (select column1 as c
union all
select column2) as cs))
from test
But no dice:
Msg 130, Level 15, State 1, Line 7
Cannot perform an aggregate function on an expression containing an aggregate or a subquery.
Is this possible in T-SQL without resorting to a procedure/temp table?
UPDATE: Eran, thanks - I used this approach. My final expression is a little more complicated, however, and I'm wondering about performance in this case:
SUM(CASE WHEN ABS(column1 * column2) > ABS(column3 * column4)
THEN column5 * ABS(column1 * column2) * column6
ELSE column5 * ABS(column3 * column4) * column6 END)
Try this:
SELECT SUM(CASE WHEN column1 > column2
THEN column1
ELSE column2 END)
FROM test
Try this... Its not the best performing option, but should work.
SELECT
'LargerValue' = CASE
WHEN SUM(c1) >= SUM(c2) THEN SUM(c1)
ELSE SUM(c2)
END
FROM Test
SELECT
SUM(MaximumValue)
FROM (
SELECT
CASE WHEN column1 > column2
THEN
column1
ELSE
column2
END AS MaximumValue
FROM
Test
) A
FYI, the more complicated case should be fine, so long as all of those columns are part of the same table. It's still looking up the same number of rows, so performance should be very similar to the simpler case (as SQL Server performance is usually IO bound).
How to find max from single row data
-- eg (empid , data1,data2,data3 )
select emplid , max(tmp.a)
from
(select emplid,date1 from table
union
select emplid,date2 from table
union
select emplid,date3 from table
) tmp , table
where tmp.emplid = table.emplid
select sum(id) from (
select (select max(c)
from (select column1 as c
union all
select column2) as cs) id
from test
)
The best answer to this is simply put :
;With Greatest_CTE As
(
Select ( Select Max(ValueField) From ( Values (column1), (column2) ) ValueTable(ValueField) ) Greatest
From Test
)
Select Sum(Greatest)
From Greatest_CTE
It scales a lot better than the other answers with more than two value columns.