If there is a table called variant
id slug slug_id
------- --------- ----------
1 s 10
1 m 10
1 l 10
1 black 11
1 pink 11
1 ship_us 12
1 ship_uk 12
2 xl 10
2 xxl 10
2 blue 11
2 white 11
Result I need in this format:
id variant_slug
-------- ------------
1 1-s-black-ship_us
1 1-s-black-ship_uk
1 1-s-pink-ship_us
1 1-s-pink-ship_uk
1 1-m-black-ship_us
1 1-m-black-ship_uk
1 1-m-pink-ship_us
1 1-m-pink-ship_uk
1 1-l-black-ship_us
1 1-l-black-ship_uk
1 1-l-pink-ship_us
1 1-l-pink-ship_uk
2 2-xl-blue
2 2-xl-white
2 2-xxl-blue
2 2-xxl-white
Q: this record is in same variant table. I have almost no experience using UDFs, stored procedures, I need to be done this thing through query. Is this possible without using UDFs, SP's.
Perhaps a self-join assuming the length of size<=3.
Select A.ID
,variant_slug = concat(A.id,'-',A.slug,'-',B.slug)
from YourTable A
Join YourTable B
on A.ID=B.ID
and A.slug<>B.slug
and len(B.slug)>3
and len(A.slug)<=3
Results
ID variant_slug
1 1-l-black
1 1-l-pink
1 1-m-black
1 1-m-pink
1 1-s-black
1 1-s-pink
2 2-xl-blue
2 2-xl-white
2 2-xxl-blue
2 2-xxl-white
Rather than len(), you can enumerate the sizes i.e. {NOT } IN ('s','m','l','xl','xxl')
Select A.ID
,variant_slug = concat(A.id,'-',A.slug,'-',B.slug)
from YourTable A
Join YourTable B
on A.ID=B.ID
and A.slug<>B.slug
and B.slug NOT IN ('s','m','l','xl','xxl')
and A.slug IN ('s','m','l','xl','xxl')
You can go for INNER JOIN by separating the table into two separate tables: size, color and get the variant data, as given below:
declare #slug table(id int, slug varchar(100))
insert into #slug values
(1,'s')
,(1,'m')
,(1,'l')
,(1,'black')
,(1,'pink')
,(2,'xl')
,(2,'xxl')
,(2,'blue')
,(2,'white');
SELECT size.id, CONCAT_WS('-',size.id,size.size, color.color) as variant_size
from (select id,slug as size from #slug where slug in ('s','m','l','xl','xxl') ) as size
INNER JOIN (select id,slug as color from #slug where slug NOT in ('s','m','l','xl','xxl') ) as COLOR
on color.id = size.id
id
variant_size
1
1-s-black
1
1-s-pink
1
1-m-black
1
1-m-pink
1
1-l-black
1
1-l-pink
2
2-xl-blue
2
2-xl-white
2
2-xxl-blue
2
2-xxl-white
I am trying to do a left join so that I get all of my rows from Table 1 even if there is no value corresponding to it in the second table.
My structures are:
Location Table:
ID LocName
1 Trk1
2 Trk2
3 Trk3
4 Unk
Quantity Table:
ID PartID Quantity LocationID
1 1 2 1
2 3 12 2
3 2 6 1
4 6 8 3
5 6 5 1
I am trying to join but also make a query on a specific PartID. My query is:
SELECT
INV_LOCATIONS.ID AS LocationID,
INV_LOCATIONS.NAME AS LocationName,
INV_QUANTITY.QUANTITY AS Quantity
FROM INV_LOCATIONS
LEFT JOIN INV_QUANTITY ON INV_LOCATIONS.ID = INV_QUANTITY.LOCATION_ID
WHERE INV_QUANTITY.PART_ID = 1;
My output right now would be:
ID LocName Quantity
1 Trk1 5
3 Trk3 8
The Desired output is:
ID LocName Quantity
1 Trk1 5
2 Trk2 NULL/0
3 Trk3 8
4 Unk NULL/0
I assume it is because I have the WHERE INV_QUANTITY.PART_ID = 1 and that is forcing it to be in the quantity table. I need to be able to verify it is on the right part but how do I also include it if it doesn't exist. I know I have done something very similar before but I cannot remember which project and so I cannot find the code anywhere.
You need to move the filtering logic to the ON clause:
SELECT il.ID AS LocationID, il.NAME AS LocationName,
iq.QUANTITY AS Quantity
FROM INV_LOCATIONS il LEFT JOIN
INV_QUANTITY iq
ON il.ID = iq.LOCATION_ID AND iq.PART_ID = 1;
I have two tables:
TypeTable
TypeId PersonClassificationId
----------------------
1 1
1 2
1 3
2 1
2 2
PersonClassificationTable
PersonClassificationId Capacity
----------------------
1 2
2 2
3 2
I need to select such TypeId that in the entire TypeTable table do not have at least one PersonClassificationID specified in PersonTable.
So, if PersonTable has 1, 2, 3, then TypeId = 2 should be selected, because there is no record in TypeTable:
TypeId PersonClassificationId
----------------------
2 3
How can I do that?
It is undesirable to use cursors : )
I think that you can do what you want by generating all possible combinations of types and classifications, and then filter on those that do not exist in the mapping table:
select t.TypeId, pc.PersonClassificationId
from (select distinct TypeId from TypeTable) t
cross join PersonClassificationTable p
where not exists (
select 1
from TypeTable t1
where t1.TypeId = t.TypeId and t1.PersonClassificationId = p.PersonClassificationId
)
I have 2 tables named user and statistics
user table has 3 columns: id, name and category
statistics table has 3 columns: id, idUser (relational), cal
something like this:
user
Id name category
1 name1 1
2 name2 2
3 name3 3
statistics
Id idUser cal
1 1 1
2 1 1
3 1 1
4 2 1
5 2 1
How can I apply a query that sum the cal column by each category of users and give me something like this:
category totalcal
1 3
2 2
3 0
You want to do a left join to keep all the categories. The rest is just aggregation:
select u.category, coalesce(sum(s.cal), 0) as cal
from users u left join
statistics s
on u.id = s.idUser
group by u.category;
Use LEFT JOIN to get 0 sum for the category=3:
SELECT
user.category
,SUM(statistics.cal) AS totalcal
FROM
user
LEFT JOIN statistics ON statistics.idUser = user.Id
GROUP BY
user.category
Here SUM would return NULL for category=3. To get 0 instead of NULL you can use COALESCE(SUM(statistics.cal), 0).
I wrote a cursor where I needed to copy some rows and insert it into a table with only 1 column different. Say for example I have a table A like this
Id | CID | Country
1 X A
2 X B
3 X C
'Id' in this table is auto increment and primary key and Country is the countries visited by that CID. So when I was asked to update the table where every country visited by CID 'X' has also been visited by CID 'Y'. I wrote a cursor and did an insert into with CID 'Y' and the Country. After I executed my cursor, table A became this:
Id | CID | Country
1 X A
2 X B
3 X C
4 Y A
5 Y B
6 Y C
Now there is another table B that is as follows, where AId is the foreign key referencing Id in A.
AId | AgeOfKids
1 20
1 23
1 28
2 21
2 24
2 29
3 22
3 25
I want to be able to add rows to this table such that it becomes:
AId | AgeOfKids
1 20
1 23
1 28
2 21
2 24
2 29
3 22
3 25
4 20
4 23
4 28
5 21
5 24
5 29
6 22
6 25
To explain in words, the AIds that have the same countries in table A must have the same BeIds in table B. Is it possible to accomplish this? Is so, how can I accomplish this?
Use the OUTPUT clause:
declare #t table (Id int not null,Country char(1) not null)
insert into TableA (CID,Country)
output inserted.id,inserted.Country into #t
select 'Y',Country from TableA where CID = 'X'
And then (should be part of the same batch as the above):
insert into TableB (AId,AgeOfKids)
select t.ID,b.AgeOfKids
from #t t
inner join
TableA a
on
t.Country = a.Country and
a.CID = 'X'
inner join
TableB b
on
a.ID = b.AId
To populate table B.