How do I get 5 values from 3 different tables? [MYSQL] - mysql

MYSQL
I am trying to get 5 values from 3 separate tables where each value is in it's own column.
The values I am trying to get are: SC_Name, SC_Description, AR_Name, AR_Description, AR_id
I have 3 tables where I am pulling the data from:
Service_Category
Area_Responsibility
Key_Scar
Service_Category contains the following columns:
id
SC_Name
SC_Description
Area_Responsibility contains the following columns:
id
AR_Name
AR_Description
Key_SCAR contains the following columns:
id
KS_id
SC_id
AR_id
The intention of having 3 separate tables is so that I can separate the data better in the first two tables and then in the third table link them together on the basis of KS_id and the id from Service_Category and the id from Area_Responsibility.
At the moment I have the following individual queries (KS_id is always 1):
SELECT a.SC_Name, a.SC_Description
FROM Service_Category AS a
where a.id IN (SELECT SC_id
FROM Key_SCAR
WHERE KS_id = 1);
SELECT a.AR_Name, a.AR_Description
FROM Area_Responsibility AS a
where a.id IN (SELECT AR_id
FROM Key_SCAR
WHERE KS_id = 1);
I would like to join these into one query that outputs: SC_Name, SC_Description, AR_Name, AR_Description and AR_id.
I have tried to union these two queries as follows:
SELECT a.SC_Name, a.SC_Description
FROM Service_Category AS a
where a.id IN (SELECT SC_id
FROM Key_SCAR
WHERE KS_id = 1)
UNION
SELECT b.AR_Name, b.AR_Description
FROM Area_Responsibility AS b
where a.id IN (SELECT AR_id
FROM Key_SCAR
WHERE KS_id = 1);
This however does not work for my output as the interpreter I'm using places AR_Name & AR_Description under the column headings SC_Name and SC_Description. I need each of the outputted values to be in their own columns.
I hope this explains it well enough, and thank you in advance for the assistance!

Here's how you can try to achieve your required results by using the join method,
SELECT SC.SC_Name, SC.SC_Description, AR.AR_Name, AR.AR_Description, KS.AR_id
FROM Key_SCAR KS
INNER JOIN Service_Category SC ON SC.id = KS.SC_id
INNER JOIN Area_Responsibility AR ON AR.id = KS.AR_id
WHERE KS.KS_id = 1;

Related

Mysql Left Join of 3 tables and a one being joined twice

I need to do a join of 3 tables.
They all have an ID value, the issue is:
Table 1
Is the main one, name : cnpj_cnae and the ID is CNPJ_CNAE
Table 2
I need to get four columns from this one (Up to here I already got it).
The ID here is CNPJ_CNAE
Table 3
Here's the issue. For each ID value on table 1 I can have more than 1 even 10 on this table. I need to get 4 columns from ONLY THE FIRST TWO of this table.
The ID here is CNPJ_SOCIO
The finishing table would need to look like
ID INFOTABLE1 INFOTABLE2 INFOTABLE3ROW1 INFOTABLE3ROW2
I have tried some joins, but being a relative newbie with mysql I am suffering >.<
I have tried to do this:
CREATE TABLE cnpj_cnae_emp_test3 AS (
SELECT
`cnpj_cnae_test2`.*,
`cnpj_soci`.NOME_SOCIO,`cnpj_soci`.CNPJ_CPF_SOCI,`cnpj_soci`.ID_QUALIFICACAO_REP,`cnpj_soci`.DESC_QUALIFICACAO_REP,
`cnpj_emp_02`.MUNICIPIO,`cnpj_emp_02`.BAIRRO,`cnpj_emp_02`.TIPO_LOGRADOURO,`cnpj_emp_02`.LOGRADOURO,`cnpj_emp_02`.NUMERO,`cnpj_emp_02`.COMPLEMENTO
FROM `cnpj_cnae_test2`, `cnpj_soci`, `cnpj_emp_02`
WHERE `cnpj_cnae_test2`.CNPJ_CNAE = `cnpj_soci`.CNPJ_SOCIO AND `cnpj_cnae_test2`.CNPJ_CNAE = `cnpj_emp_02`.CNPJ
);
The issue is this will generate extra rows for every SOCI where instead of 1 soci on each one I need 2 socis on each line.
Table 1:
Layout of CNAE table
Table 2:
Layout of EMP table
Table 3:
Layout of Socio table
The resulting table would look like this:
More detailed end result Final layout with descriptions
Layout of result
In the end this by Owl was exactly what I needed:
WITH soci_partition AS (
SELECT CNPJ_SOCIO
,NOME_SOCIO
,CNPJ_CPF_SOCIO
,ID_QUALIFICACAO
,DESC_QUALIFICACAO_SOCIO
,row_number() OVER (PARTITION BY CNPJ_SOCIO ORDER BY IDX ASC) AS rownum
FROM cnpj_soci
)
SELECT * -- add actual columns
FROM cnpj_cnae_test2 AS cnae
INNER JOIN cnpj_emp_02 AS emp -- left join instead? depends on table structure
ON cnae.ID_CNAE = emp.IDX
LEFT JOIN soci_partition AS soci1
ON soci1.CNPJ_SOCIO = cnae.CNPJ_CNAE and soci1.rownum = 1
LEFT JOIN soci_partition AS soci2
ON soci2.CNPJ_SOCIO = cnae.CNPJ_CNAE and soci2.rownum = 2
Not sure if I got the joins/partition right, the foreign keys weren't clear.
Even if it's not perfect, hopefully this explains the general theory. Please edit in your correct answer if you end up debugging.
Also don't use old-style joins. You'll immediately fail interviews on that alone; they were deprecated 25 years ago.
WITH soci_partition AS (
SELECT CNPJ_SOCIO
,NOME_SOCIO
,CNPJ_CPF_SOCIO
,ID_QUALIFICACAO
,DESC_QUALIFICACAO_SOCIO
,row_number() OVER (PARTITION BY CNPJ_SOCIO ORDER BY IDX ASC) AS rownum
FROM cnpj_soci
)
SELECT * -- add actual columns
FROM cnpj_cnae_test2 AS cnae
INNER JOIN cnpj_emp_02 AS emp -- left join instead? depends on table structure
ON cnae.ID_CNAE = emp.IDX
LEFT JOIN soci_partition AS soci1
ON soci1.CNPJ_SOCIO = cnae.CNPJ_CNAE and soci1.rownum = 1
LEFT JOIN soci_partition AS soci2
ON soci2.CNPJ_SOCIO = cnae.CNPJ_CNAE and soci2.rownum = 2
Give a try to below query
select * from cnae t1
left join emp t2 on t1.cnpj_cnae = t2.cnpj
left join socio t3 on t1.cnpj_cnae = t2.cnpj_socio
group by idx_cnae ;

Count field and group by regarding another field on same table MySQL

I am trying to find count of field by another field in same table on MySQL.My Table Like This:
Id DrgId CodeType IsPrincipal Code
182250051 48261836 I 1 T151
182250055 48261836 I 2 U739
182250059 48261836 I 3 Y929
182250061 48261836 I 4 W444
182250062 48261836 A 2 3006104
So I want to find used helper codes for T151 which is IsPrincipal equals 1.
Output should like this:
Code Helper_I_Count Helper_A_Count
T151 3 1
So I tried Like this:
SELECT t.`Code`,COUNT(v1.`Code`) AS EkTaniSay,COUNT(v2.`Code`) AS IslemSay
FROM TIGPatientCode t,
(
SELECT DRGPatientId,`Code`
FROM TIGPatientCode
WHERE IsPrincipal<>'1' AND CodeType='I'
) v1,
(
SELECT DRGPatientId,`Code`
FROM TIGPatientCode
WHERE IsPrincipal<>'1' AND CodeType='A'
) v2
WHERE t.IsPrincipal='1' AND t.DRGPatientId=v1.DRGPatientId AND t.DRGPatientId=v2.DRGPatientId
GROUP BY t.`Code`
But it wont get actual count.
How can I Do this?
Thanks
SELECT t2.Code,
SUM(t1.CodeType = 'I') AS EkTaniSay,
SUM(t1.CodeType = 'A') AS IslemSay
FROM TIGPatientCode AS t1
RIGHT JOIN TIGPatientCode AS t2 ON t1.DrgPatientId = t2.DrgPatientId
WHERE t1.isPrincipal != 1 AND t2.isPrincipal = 1
GROUP BY t1.DrgPatientId;
The first part of the query is based on multiple query same table but in different columns mysql. Then I join this with the table again to get the code for the principal row.
The problem with your query is that joining the two subqueries creates a cross-product of all the rows, which causes the counts to be multiplied. Also, if there's any group that doesn't have one of the codes, that subquery will return no rows, so the join will be empty for that code. You could fix the first problem by doing the counts in the subqueries rather than the main query. The second problem can be fixed by using LEFT JOIN. So the fixed version of your query would look like:
SELECT t.Code, v1.EkTaniSay, v2.IslemSay
FROM TIGPatientCode t
LEFT JOIN (
SELECT DRGPatientId, COUNT(*) AS EkTaniSay
FROM TIGPatientCode
WHERE IsPrincipal<>'1' AND CodeType='I'
GROUP BY DRGPatientId
) AS v2 ON t.DRGPatientId = v2.DRGPatientId
LEFT JOIN (
SELECT DRGPatientId, COUNT(*) AS IslemSay
FROM TIGPatientCode
WHERE IsPrincipal<>'1' AND CodeType='A'
GROUP BY DRGPatientId
) AS v1 ON t.DRGPatientId = v1.DRGPatientId
WHERE t.IsPrincipal = 1
DEMO

Cross Referencing Multiple Tables

What I was trying to do is to get data from multiple tables, supposed that I have the following results in my query:
The numbers in the column ticket_item_type represents certain table. For example, 2 is for tbl_company and 3 is for tbl_lease. Then the details represents the id of a certain record in that table.
Suppose that I want to get the title of those records using ticket_item_type and details. Is it possible to embed it to the results? Or should I make separate queries for each.
I know JOIN, but I is it only for single table?
Here's my MYSQL query for the image above:
SELECT *
FROM
(SELECT *
FROM ticket_items
WHERE hs_customer = 1
AND ticket IN
(SELECT id
FROM tickets
WHERE hs_customer='1'
AND ticket_status = 'dispatch_reviewed')
AND ticket IN
(SELECT ticket
FROM ticket_items
WHERE ticket_item_type = 5
AND details = '159')) AS TB1
WHERE ticket_item_type IN (3,
2,
8)
You could try something like this:
SELECT
TB1.*,
CASE
WHEN TB1.ticket_item_type = 2 THEN t2.title
WHEN TB1.ticket_item_type = 3 THEN t3.title
WHEN TB1.ticket_item_type = 8 THEN t8.title
ELSE 'NA'
END as title
FROM
(
SELECT *
FROM ticket_items
WHERE hs_customer = 1
AND ticket IN (SELECT id FROM tickets WHERE hs_customer='1' AND ticket_status = 'dispatch_reviewed')
AND ticket IN (SELECT ticket FROM ticket_items WHERE ticket_item_type = 5 AND details = '159')
) AS TB1
LEFT JOIN tbl_company t2 ON TB1.details = t2.id
LEFT JOIN tbl_lease t3 ON TB1.details = t3.id
LEFT JOIN tbl_next t8 ON TB1.details = t8.id
WHERE ticket_item_type IN (3, 2, 8)
However, this is not a design that I would prefer. Without looking at details of your database it's going to be hard to write a query to cover multiple types of ticket_item_type. I hope this query works for you, though.

SQL SELECT from 3 tables

ft_pupils
- id //Primary Key
- name
- start_date
ft_entries
- id
- pupil_id //Foreign Key
- aol_id
ft_aol
- id
- title
For every entry in the ft_entries table I want to use a SELECT to select every entry in the ft_entries table but with the aol_id replaced with the title inside of ft_aol.
I have managed to get:
SELECT name, aol_id FROM ft_pupils, ft_entries WHERE pupil_id = ft_pupils.id
to work fine.
I want the WHERE to be WHERE pupil_id = ft_pupils.id
I am so confused right now.
You can try this to get what you want by join 3 table.
SELECT Name,title FROM ft_entries
INNER JOIN ft_pupils ON pupil_id = ft_pupils.id
LEFT JOIN ft_aol ON ft_aol.id = aol_id
This will show you how to get the data you're looking for and display all the ids. You can remove the ids if you don't care to see them:
SELECT a.id,
b.pupil_id,
c.id,
a.NAME,
a.start_date,
c.title
FROM ft_pupils a
JOIN ft_entries b ON a.id = b.pupil_id
JOIN ft_aol c ON c.id = b.aol_id

Select values from table with multiple attributes

I have 3 tables:
1: products (id, name)
2: product_attributes (attribute_id, name)
3: product_attributes_selected (product_id, attribute_id,value)
Now I want to get all product_id that have two or more desired attributes and values
How can I accomplish that?
I tried this, but it failed:
select p.id,p.nazwa_pl
from produkty p,produkty_atrybuty_wartosci paw
where (paw.atrybut_id=2 and paw.wartosc=4)
and (paw.atrybut_id=3 and paw.wartosc=0)
and p.id=paw.produkt_id
group by p.id
I'n my example we have a table named Attribs, some how you need to create (e.g. TABLE variable, or CTE or some other way), my code will show you how to JOIN it.
CREATE TABLE Attribs( Attrib INT, Val INT )
^^ Populate some data in it... (again could be automated) ^^
select p.id,p.nazwa_pl
from produkty p
JOIN produkty_atrybuty_wartosci paw
ON p.id=paw.produkt_id
JOIN Attribs AS A
ON A.Attrib = paw.atrybut_id
AND A.Val = paw.wartosc
With the following query you get all ids. The idea is the following: you get all products that have the attribute 2 OR 3 OR 4. Afterwards, you group the result by the product id and count the grouped items (grouped). Only those entries that group 3 entries (you are searching for 3 attribute ids) are sufficient. Obviously, the resulting products can have more attributes, but you asked for at least the provided attributes.
SELECT p.id, p.nazwa_pl, paw.bibkey, paw.keywordid, COUNT(*) as grouped
FROM produkty p, produkty_atrybuty_wartosci paw
WHERE p.id=paw.produkt_id AND paw.atrybut_id IN (2, 3, 4) GROUP BY p.id
HAVING grouped = 3;
Having a table1 resource with columns {'id','name',....} and a table2 resource_attribute with columns {'id','resource_id','attribute_name','attribute_value'} where column resource_id is a foreign key pointing to Resource.id, you can do it in this way:
SELECT r.* FROM resource r LEFT JOIN resource_attribute ra ON r.id = ra.resource_id
AND (
(ra.NAME = 'height' AND ra.VALUE = '20') #First attribute
OR
(ra.NAME = 'color' AND ra.VALUE = 'blue') #Second attribute
)
GROUP BY r.id
HAVING COUNT(*) = 2 #Total number of attributes searched
of course if you want to make it dynamic, and use the attributes name and values you need, you can save the number of attributes you want to use in your query and reuse it in the final COUNT(*) function.
I use this query dynamic in my code (java) and it works.
Actualy I found ansfer that works for me
SELECT p.id,p.nazwa_pl FROM produkty p JOIN produkty_atrybuty_wartosci paw ON p.id=paw.produkt_id WHERE (paw.atrybut_id,paw.wartosc) IN ((2,4),(3,0)) GROUP BY p.id, p.nazwa_pl HAVING COUNT(DISTINCT paw.atrybut_id)=2
Thanks for Your help and time