Combining item and it's category into single column - sql

I'm in need of combining two columns into one in a specific way.
Here are the columns.
Column A (Items) Column B (Category)
Item 1 Category A
Item 2 Category A
Item 3 Category B
Item 4 Category B
Item 5 Category C
Item 6 Category C
...
What i want to achieve is something like this
Column AB
Category A
Item 1
Item 2
Category B
Item 3
Item 4
Category C
Item 5
Item 6
Please advise as i have a feeling that there is a simple resolution for this issue i just can't find it.
Thanks !

Try this
with wt1
as(
select distinct t2.col2 as col1,t2.col2
from tst t2
union all
select t1.col1,t1.col2
from tst t1
)
select col1
from wt1
order by col2,col1;
Output:
COL1
A
item1
item2
B
item3
item4
C
item5
item6

If I understood well, you want all items plus the distinct categories.
The result should be ordered by the category first and then by the item.
You could try something like this:
SELECT ColumnAB
FROM (
SELECT columnB AS Category
columnA AS ColumnAB,
2 AS ColumnType
FROM my_table
UNION ALL
SELECT DISTINCT
columnB AS Category
columnB AS ColumnAB,
1 AS ColumnType
FROM my_table
ORDER BY Category,ColumnType,ColumnAB
)

Related

How to get distinct count over multiple columns in SQL?

I have a table that looks like this. And I want to get the distinct count across the three columns.
ID
Column1
Column 2
Column 3
1
A
B
C
2
A
A
B
3
A
A
The desired output I'm looking for is:
ID
Column1
Column 2
Column 3
unique_count
1
A
B
C
3
2
A
A
B
2
3
A
A
1
You want to use cross apply for this one.
select *
from t cross apply
(select count(distinct cnt) as unique_count
from (values(Column1),(Column2),(Column3)) t(cnt)) t2
ID
Column1
Column2
Column3
unique_count
1
A
B
C
3
2
A
A
B
2
3
A
A
1
Fiddle
In standard SQL, you have to UNPIVOT first, do the count(distinct) group by on the PIVOTed result and then PIVOT again.
In recent ORACLE version, you could write your own Polymorphic Table Function to do it, passing the table and the list of columns to count for DISTINCT values.
try if this works
SELECT Count(*)
FROM (SELECT DISTINCT Column1 FROM TABLENAME);

SQL query 'Join'

TABLE A >>
ItemNo Name
1 Item1
2 Item2
3 Item3
4 Item4
TABLE B >>
ItemNo Status
1 available
1 onhold
1 Sold
1 Transit
------------------
2 available
2 onhold
2 Sold
-----------------
3 Transit
-----------------
4 onhold
There are four status on table B onhold,available,sold,Transit
Expected result: if anyone of the itemNo in table B has on either available or Transit,
then I need to get only the table A record of that ItemNo
Output:
Table A:
ItemNo Name
1 Item1
2 Item2
3 Item3
Please advise on how to write MS SQL query for this. Many thanks in advance!
You can solve with a correlated subquery:
SELECT *
FROM tableA ta
WHERE tA.ItemNo IN
(
SELECT tB.ItemNo
FROM tableB tB
WHERE tB.Status in ('available','Transit')
AND tB.ItemNo = ta.ItemNo
)
Join the tables and use SELECT DISTINCT to get just one row from table A.
SELECT DISTINCT a.*
FROM TableA AS a
JOIN TableB AS b ON a.itemNo = b.itemNo
WHERE b.status in ('available', 'Transit')

Selecting all rows from t1 join t2 on id and select the lowest value from t2 or null if not any

I have two tables, one holds some categories and the other holds players' records like so:
Categories Times
id Name id UserId MapId CategoryId Time
1 cat1 1 1 1 1 1500
2 cat2 2 3 1 2 3000
3 cat3 3 13 1 3 2500
4 cat4 4 12 1 4 1500
5 cat5 5 11 1 4 1000
I want to select all the categories (id, name) and the lowest time on each category.
If there's no record on that category it should show NULL or 0.
This would be the expected result:
Result
id Name Time
1 cat1 1500
2 cat2 3000
3 cat3 2500
4 cat4 1000
5 cat5 0
I'm using the following query, but it only selects the categories that already have a record in Times.
For example, if I use the following query it'll not select 'cat5' because it doesn't have any record in table Times.
select t2.id, t2.Name, min(t1.Time) as Time
from Times t1
join Categories t2 on t2.id = t1.CategoryId
where t1.MapId = %MAPID%
group by t2.id
I recommend to begin your query with the table "categories" in this case since your focus is on the data from this table. So you could write a left join. Furthermore, I think it's a good idea to replace null values by zero, thus your query would as example find negative times as the lowest times and return 0 if the lowest time is a null value.
Overall, this could be your goal:
SELECT c.id, c.name, MIN(COALESCE(t.time,0)) AS time
FROM categories c LEFT JOIN times t ON c.id = t.categoryid
GROUP BY c.id, c.name;
Here is a working example according to your sample data: db<>fiddle
There are likely also other options to achieve your goal, you can just try out.
I think you might just need to do a right join (because you want all rows from the 2nd table listed -- Categories). See if you get the desired results by changing line 3 to be:
right join Categories t2 on t2.id = t1.CategoryId

add value from different tables and insert total value into another table

I have several tables (say 5 tables) and I want to sum a specific entry from each of the 5 tables and put that sum in one table.
Example:
Table_One
product_one_id name price
1 item1 50.25
2 item2 100.25
Table_Two
product_two_id name price
1 item3 25.25
2 item4 70.25
Table_Total
product_total_id name price_total
1 total1 120.50 //get total from item1 + item4
2 total2 125.50 //get total from item2 + item3
this my code: is not a correct syntax but to illustrate what I'm trying to do
INSERT INTO Table_Total(product_total_id, name, price_total)
VALUES (1, 'total1', ((select price from Table_One where product_one_id = 1) + (select price from Table_Two where product_two_id = 4));
While I'm not completely sure why you need to do this, this should work using a cross join which essentially produces a cartesian product:
insert into table_total
select 1, 'total1', t1.price + t2.price
from table_one t1 cross join table_two t2
where t1.table_one_id = 1
and t2.table_two_id = 2;
SQL Fiddle Demo

Get unique common records with all records from both tables?

Hi I have two tables structure is like this
Table 1
Customer Company price qty item invno
1 a 89 8 item1 23
2 b 80 4 item2 22
3 c 90 3 item1 45
4 d 19 6 item3 12
table 2
Customer Company price qty item invno
1 a 89 8 item1 23
2 b 80 4 item2 18
3 c 90 3 item1 45
4 d 19 6 item3 15
basically table1 contains the current records and table2 current+past records and they both have other columns
what i want is get the all records from the table1 and table2 but in case of the duplication of invno i need that record from the table1 in this case resultset will contains the invno-23(table1),22(table1),45(table1),12(table1),18(table2),15(table2)
I tried using UNION but it gives different results on different column selection i stuck here any help would be great .
Here is one method, using union all and a filter:
select *
from table1 t1
union all
select *
from table2 t2
where not exists (select *
from table1 t1
where t1.invno = t2.invno
);
SELECT t2.Customer,
t2.Company,
t2.price,
t2.qty,
t2.item,
IFNULL(t1.invno,t2.invno)
FROM table2 AS t2
LEFT JOIN table1 AS t1
ON t2.Customer=t1.Customer