Concatenate rows based on multiple column values - sql

I am trying to get a new column with a concatenation of all distinct row values. This aggregation would be based on other columns.
I have tried the following but I get the same values repeated in the new column (A1, A1, A4). I need the concatenation to be distinct.
SELECT
STRING_AGG(COLUMN1, ', ') AS COLUMN1_ALIAS
,COLUMN2
,COLUMN3
,COLUMN4
FROM TABLE
GROUP BY COLUMN2 ,COLUMN3 ,COLUMN4

It looks like you want windowing rather than aggregation. Unfortunately, string_agg does not support over() in SQL Server ; neither does it support distinct in its aggregated form.
We could work around it with subqueries ; it is probably more efficient to deduplicate and pre-compute the aggregates first, then join with the original table:
select t.*, x.column1_alias
from mytable t
inner join (
select column2, column3, column4, string_agg(column1, ', ') as column1_alias
from (select distinct column1, column2, column3, column4 from mytable) t
group by column2, column3, column4
) x on x.column2 = t.column2 and x.column3 = t.column3 and x.column4 = t.column4
Side note : in a database that supports both over() and distinct on string aggregation, the query would phrase as:
select t.*,
string_agg(distinct column4, ', ')
over(partition by column2, column3, column4) as column1_alias
from mytable t

Related

Is there a function in SQL that allows me to sum specific rows based on a column value?

I want to sum City4, and the two misspellings together as one row. Any input on how to do this?
SELECT column1,
column2,
count(column3),
Sum(Column4)
FROM TABLE
AND column1 IN ('state1',
'State2',
'State3')
AND column2 IN ('City1',
'City2',
'City3',
'City4',
'City4 misspelled1',
'City4 misspelled 2')
GROUP BY column1,
column2
ORDER BY column1;

T-SQL Group By summarize fields using logical functions

How can I aggregate and arrive to these results?
SELECT *
FROM TABLE
GROUP BY Column1
Assuming the columns actually contain the literal string values 'TRUE' and 'FALSE', we could use:
SELECT
Column1,
MAX(Column2) AS Column2,
MAX(Column3) AS Column3
FROM yourTable
GROUP BY
Column1;

Changing column in set update

Can I use a case statement in Set Column? I have multiple columns that need to be updated but the statement is quite similar. The only difference is what I'm selecting.
UPDATE TABLE1 A
SET A.COLUMN2 = (SELECT....
I want to update column2 to Column1 without repeating the same block of code.
Note: I'm using LISTAGG
Is there any way I could distinct both of the columns without trying to separate it in one query the make a subquery
I'm using this query and I know that listagg don't have the capabilities to distinct unless you distinct it first before using listagg
SELECT LISTAGG(COLUMN1 , ', ') WITHIN GROUP (ORDER BY COLUMN1) AS COLUMN1 ,
LISTAGG(COLUMN2 , ', ') WITHIN GROUP (ORDER BY COLUMN2) AS COLUMN1
FROM (SELECT COLUMN1 , COLUMN2 FROM TABLE2 B
WHERE A.COLUMN3 = B.COLUMN3
GROUP BY COLUMN1 , COLUMN2);
COLUMN1 COLUMN2
EGG PIE
EGG BREAD
Expected output
COLUMN1 COLUMN2
EGG PIE; BREAD
Do you mean
UPDATE table1
SET (column1, column2 ...) = (SELECT col1, col2 ...)

Group by on a column with duplicates (string values)

I have to create a MS SQL Query on the table below.
Consider I have following single table:
I want to get the following result by grouping on column1:
How can I accomplish this?
Use COUNT with GROUP BY.
Query
SELECT column1, 'N/A' as column2, 'N/A' as column3,
COUNT(column1) AS column4_amount
FROM your_table_name
GROUP BY column1;
SELECT column1, 'N/A' as column2, 'N/A' as column3, COUNT(1) AS column4_amount
FROM table_name
GROUP BY column1
if you don't need column2 and column3 then try below:
SELECT column1, COUNT(1) AS column4_amount
FROM table_name
GROUP BY column1
Update:
As you want results which has more than one occurrence, try this:
SELECT column1, 'N/A' as column2, 'N/A' as column3, COUNT(1) AS column4_amount
FROM table_name
GROUP BY column1
HAVING COUNT(1) > 1
You should use GROUP BY with column1 as GROUP BY helps you group all the items with the same name.
To count total items under a group of items, from the table with the same name, use the COUNT aggregate function. Now you need to check that each item exists more than once. Use the HAVING clause which takes all the groups that have more than two items.
SELECT column1, 'N/A' as column2, 'N/A' as column3, COUNT(1) AS column4_amount
FROM your_table_name
GROUP BY column1
HAVING COUNT(1) > 1

Finding rows that have many similar values and one different one

I'm trying to isolate a problem with a violation of a unique key index. I'm pretty certain that the cause is resulting from columns that have the same value in 3 columns not having the same value in the 4th (when they should). As an example...
Key Column1 Column2 Column3 Column4
1 A B C D
2 A B C D
3 A B C D
4 A B C Z
I basically want to select column 4, or some way to let me identify column 4. I know it's a matter of using aggregrate functions but I'm not very familiar with them. Can anyone assist on a way to select Key, Column4 for rows that have a different column 4 value and the same column 1-3 values?
This is what you want:
select column1, column2, column3
from t
group by column1, column2, column3
having min(column4) <> max(column4)
Once you get the right values for the first three columns, you can join back in to get the specific rows.
Or, you can use window functions like this:
select t.*
from (select t.*, min(column4) over (partition by column1, column2 column3) as min4,
max(column4) over (partition by column1, column2 column3) as max4
from t
) t
where min4 <> max4;
If NULL is a valid "other" value that you want to count, you will need additional logic for that.
If you want to get all columns, then (it could be simpler if windowed count supported distinct but it's not):
with cte1 as (
select distinct * from Table1
), cte2 as (
select
*,
count(column4) over(partition by column1, column2, column3) as cnt
from cte1
)
select * from cte2 where cnt > 1;
if you want just to select key:
select
column1, column2, column3
from Table1
group by column1, column2, column3
having count(distinct column4) > 1
sql fiddle demo