This question already has answers here:
How to concatenate text from multiple rows into a single text string in SQL Server
(47 answers)
Closed 9 years ago.
i have a table like this
ID NAME Amount
1 cal 100
2 cal 200
3 cal 300
4 cal 400
1 ser 500
2 ser 600
5 ser 700
i want to write a select query so that i wil get the resul like this
ID NAME Amount
1 cal and ser 600
2 cal and ser 800
3 cal 300
4 cal 400
5 ser 700
here i need to group by id and sum of amount and concat the string name with same id and differnet name
this will work with sql-server 2008
SELECT p1.ID,
( SELECT NAME + ' and '
FROM YourTable p2
WHERE p2.ID = p1.ID
ORDER BY NAME
FOR XML PATH('') ) AS Name,
sum(Amount)
FROM YourTable p1
GROUP BY ID ;
SELECT p1.ID,
STUFF(( SELECT ' and ' + NAME
FROM YourTable p2
WHERE p2.ID = p1.ID
ORDER BY NAME
FOR XML PATH('') )
, 1, 5, '' ) AS Name,
sum(Amount)
FROM YourTable p1
GROUP BY ID
From Vikram answer
I add stuff for my result.
Related
I m using pivot and unpivot but I dot get expected output
Here is my sample data set
Table 1
id c_code
-----------------
123 1
456 1
Table 2
id c_code i_t_code i_code
----------------------
123 1 TWinc 10
123 1 TBinc 20
123 1 TSinc 30
Table 3
i_code i_t_code i_name
------------------------------
10 TWinc abc
20 TBinc xyz
30 TSinc pqr
Here is my query
Query
select * from (
select id,inc,i_t_code from (
select a.id,b.i_name,cast(b.i_code AS
VARCHAR(128)) as i_code,b.i_t_code
from
table_1 a
join
table_2 b
on a.id= b.id
and
a.c_code = b.c_code
join
tabl_3 c on c.i_code = b.i_code
and
c.i_t_code = b.i_t_code
on a.i_code = b.i_code
) d
Unpivot
(
inc for details in (i_name,i_code)
) as unpt) as uppt_res
PIVOT
(
max(inc)
FOR [i_t_code] IN ([TWinc],[TBinc],[TSinc])
) AS P
Expected output:
id TWinc_n TWinc_c TBinc_n TBinc_c TSinc_n TSinc_c
------------------------------------------------------------
123 abc 10 xyz 20 pqr 30
Actual output:
id TWinc TBinc TSinc
------------------------------------
123 abc xyz pqr
How can do this ??
It is possible using pivot or any other solution is there
can anyone help to fix this ?
You're going to have to give your data some variation if you want to stop pivot from compressing equal data items together when it's converting row data into column names and picking the max(inc) - probably easiest to do by changing the contents of the unpivoted data, tacking on a row number:
SELECT * FROM
(
select stoneid, inc, CONCAT(inclusion_type_id, ROW_NUMBER()OVER(PARTITION BY inclusion_type_id ORDER BY inc)) as inclusion_type_id FROM
(
select
a.stoneid,
b.inclusion_name,
cast(b.inclusion_code AS VARCHAR(128)) as inclusion_code,
b.inclusion_type_id,
b.inclusion_type_code
from
PACKET.STONE_LAB_INCLUSIONS a
inner join
MASTER.INCLUSION_MASTER b
on
a.inclusion_code = b.inclusion_code and
a.inclusion_type_code = b.inclusion_type_code
inner join
packet.stone_details c
on
c.stoneid = a.stoneid and
c.certificate_code = a.certificate_code
) d
UNPIVOT(inc for details in (inclusion_name,inclusion_code)) as unpt
) uppt_res
PIVOT
(
MAX(inc)
FOR [inclusion_type_id] IN ([TWinc1],[TWinc2],[TBinc1],[TBinc2],[TSinc1],[TSinc2])
) AS P
If you're desperate to have column names the same, you can alias the results of this query rather than select *
I have a query result that is almost perfect except for the fact that in the result I don't always have a complete series in my muli-series data that I am trying to eventually show in a report and chart.
NAME MONTH COST
----------------------------------------
name1 2 100
name1 3 80
name2 1 60
name3 2 30
----------------------------------------
Here is query:
select Name, month, count(*) as cost
from table1
group by name, month
order by month, name
What I have here isn't one simple set of data, but a series of data. For each month, I have a set of users and sales.
I can fix this on my application side by doing a few loops and getting the distinct values for Name and Month.
I'd like to learn how to create my Oracle query to get a result set that looks something like this
NAME MONTH COST
----------------------------------------
name1 1 0
name1 2 100
name1 3 80
name2 1 60
name2 2 0
name2 3 0
name3 1 0
name3 2 30
name3 3 0
----------------------------------------
You can do this with a cross join and then a left outer jon:
select n.name, m.month, coalesce(t.cost, 0) as cost
from (select distinct name from table t) n cross join
(select distinct month from table t) m left join
table t
on t.name = n.name and t.month = m.month
order by n.name, m.month;
I have a table which contains data in this format.
ProductID ShipId
11 1
11 2
11 3
22 1
22 2
33 1
33 2
Now I want only the distinct product ids where ship id 3 is not associated.
Output should be
22,33 only.
I have used this query but it throws error.
Select distinct productid from X_product_ship group by productid having shipid <> 3
Please help.
Use a subquery in the where clause to exclude the products that has a shipid of three.
select distinct P1.ProductID
from dbo.X_product_ship as P1
where P1.ProductID not in (
select P2.ProductID
from dbo.X_product_ship as P2
where P2.ShipId = 3
)
SQL Fiddle
Or you could get creative in the having clause using a case statement.
select P.ProductID
from dbo.X_product_ship as P
group by P.ProductID
having max(case when P.ShipId = 3 then 1 else 0 end) = 0
SQL Fiddle
This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Combining rows of queried results by unique identifier?
I have two tables in Sql Server 2008, like below
Table1
DealNum DealVresion Value
1000 1 100
1000 2 200
1000 3 150
1000 4 130
1001 2 70
1003 5 160
1003 0 120
Table 2
DealNum DealVersion Name
1000 1 John
1000 1 Bob
1000 2 John
1000 2 Merle
1000 3 Bob
1000 3 Bob
1000 5 Bob
1001 2 Smith
1001 2 stone
1002 8 Andrew
1003 5 Smith
1003 0 Martin
1003 0 Narine
Now I want a left join on these two tables based on
(T1.Dealnum= T2.Dealnum) and (T1.Deal Version = T2.Deal Version)
and I want the Name from Table2 to be concatenated so that it won't show any duplicates in DealNum.
Result Required:
DeaLNum Deal Version Value Name
1000 1 100 Jhon,Bob
1000 2 200 John,Merle
1000 3 150 Bob
1000 4 130 NULL
1001 2 70 Smith,Stone
1003 0 120 Martin,Narine
1003 5 160 Smith
It has to concatenate the names column for the DealNum and version.
If the same dealNum and Version has the same name then no need to Concatenate(ex: 1000 - 3)
Thanks In advance
Harry
You can do this by creating a user defined function, don't know if it can be done in a single select statement:
create function getNameList(#dealnum int, #dealversion int) returns nvarchar(max)
begin
declare #name varchar(max)
select #name = coalesce(#name + ', ','') + name
from (select distinct name from table2 where dealnum = #dealnum and dealversion = #dealversion) t1
return #name
end
then:
select distinct
t1.dealNum,
t1.dealVersion,
t1.value,
dbo.getNameList(t1.dealNum, t1.dealversion)
from table1 t1 join table2 t2 on t1.dealnum = t2.dealnum and t1.dealversion = t2.dealversion
try this:
with cte as (
select distinct T1.DealNum [T1_DealNum],T1.DealVresion [T1_DealVresion],
T1.Value [T1_Value],
T2.DealNum [T2_DealNum],T2.DealVresion [T2_DealVresion],T2.Name [T2_Name]
from Table1 T1 left outer join Table2 T2
on (T1.Dealnum= T2.Dealnum) and (T1.DealVresion = T2.DealVresion)
)
select [T1_DealNum],[T1_DealVresion],[Name]=
STUFF((SELECT ', ' + [T2_Name]
FROM cte b
WHERE a.[T1_DealNum]= b.[T2_DealNum]
and a.[T1_DealVresion] = b.[T2_DealVresion]
FOR XML PATH('')), 1, 2, '')
FROM cte a
GROUP BY [T1_DealNum],[T1_DealVresion]
order by [T1_DealNum],[T1_DealVresion]
;WITH y AS
(
SELECT DealNum, DealVersion, Name = STUFF((SELECT ',' + y2.Name
FROM dbo.Table2 AS y2
WHERE y2.DealNum = y.DealNum AND y2.DealVersion = y.DealVersion
GROUP BY y2.Name
FOR XML PATH(''),
TYPE).value(N'./text()[1]', N'nvarchar(max)'), 1, 1, '')
FROM dbo.Table2 AS y
)
SELECT x.DealNum, x.DealVersion, x.Value, y.Name
FROM dbo.Table1 AS x
LEFT OUTER JOIN y
ON x.DealNum = y.DealNum
AND x.DealVersion = y.DealVersion
GROUP BY x.DealNum, x.DealVersion, x.Value, y.Name;
I am trying to combine rows from one table with my query in MS SQL on server 2008. I pulled this code off here I believe. This almost fits my needs but it is grouping the serial numbers off of SOPartsUsed but I need it to group based off tblServiceOrders.ProjectKeyID. Any help would be greatly appreciated I don't know much about SQL. I will leave a more detailed explanation of what I am trying to accomplish below.
SELECT
p1.ItemID, SerialNumbers AS SerialNumber
FROM
tblSOPartsUsed p1 INNER JOIN
tblServiceOrders p2 ON p1.SONumber = p2.SONumber
CROSS APPLY
(SELECT
stuff
((SELECT ',' + p3.SerialNumber
FROM tblSerialNumbers p3
WHERE p3.FKSOPartsUsed = p1.SOPartsUsedKeyID
ORDER BY SerialNumber FOR XML PATH(''), TYPE ).value('.', 'varchar(max)'), 1, 1, '')
) D (SerialNumbers)
WHERE (p1.QuantityFilled > 0) AND (p2.ProjectKeyID = 385)
GROUP BY p1.ItemID, SerialNumbers, p2.ProjectKeyID
ORDER BY p1.ItemID
I have a table with serial numbers a table with parts used on a service order and a service order table.
tblSerialNumbers -> tblSOPartsUsed -> tblServiceOrders
tblSerialNumbers
itemID SerialNumber FKSOPartsUsed
1 1444 233
1 1555 234
1 1666 236
1 1999 237
1 1888 238
1 2222 239
1 2121 240
tblSOPartsUsed
itemID SOPartsUsed SONumber QuantityFilled
1 233 SO544 5
1 234 SO544 7
1 236 SO544 7
1 237 SO577 7
1 238 SO577 7
1 239 SO581 7
1 240 SO580 7
tblServiceOrders
SOnumber ProjectKeyID
SO544 PJ366
SO577 PJ366
SO580 PJ111
SO581 PJ111
What I would like
itemID ProjectKeyID SerialNumber
1 PJ366 1444,1555,1666,1999,1888
What I get
itemID ProjectKeyID SerialNumber
1 PJ366 1444,1555,1666
1 PJ366 1999,1888
I am trying to group serial numbers and item id's by ProjectKeyID found in tblServiceOrders. Right now the query above works but it is grouping ItemID's on the tblSOPartsUsed and want to group on ProjectKeyID.
Thanks for any help.
SELECT itemID ,
ProjectKeyID ,
( SELECT SerialNumber + ', ' AS 'data()'
FROM dbo.tblSOPartsUsed u
JOIN tblSerialNumbers nbr ON u.SOPartsUsed = nbr.FKSOPartsUsed
WHERE SONumber IN ( SELECT SOnumber
FROM dbo.tblServiceOrders
WHERE ProjectKeyID = tso.ProjectKeyId )
AND itemID = tso.itemID
FOR
XML PATH('')
)
FROM ( SELECT DISTINCT
c.itemID ,
ProjectKeyId
FROM dbo.tblServiceOrders a
JOIN dbo.tblSOPartsUsed b ON a.SOnumber = b.SONumber
JOIN dbo.tblSerialNumbers c ON b.SOPartsUsed = c.FKSOPartsUsed
) tso
I don't think I totally understand what you're trying to accomplish with itemID - having only one distinct value in the sample makes it hard to verify results - but this might get you closer
try this
SELECT
p1.ItemID, p2.ProjectKeyID,D.SerialNumbers AS SerialNumber
FROM
tblSOPartsUsed p1 INNER JOIN
tblServiceOrders p2 ON p1.SONumber = p2.SONumber
CROSS APPLY
(SELECT
stuff
((SELECT ',' + p3.SerialNumber
FROM tblSerialNumbers p3
WHERE p3.ItemID = p1.ItemID
ORDER BY SerialNumber FOR XML PATH(''), TYPE ).value('.', 'varchar(max)'), 1, 1, '')
) D (SerialNumbers)
WHERE (p1.QuantityFilled > 0) AND (p2.ProjectKeyID = 'PJ366')
GROUP BY p1.ItemID, p2.ProjectKeyID, SerialNumbers
ORDER BY p1.ItemID