SQL Server : compare two CTE Tables - sql-server

I would like to compare two CTES tables. The purpose of this is that i would like to see which PersonKey(PK) exists in another CTE table i have created. So i could match the data after.
WITH cte1 AS
(
SELECT DISTINCT 1.PERSON_CODE,la.AIM
FROM [PEOPLE_UNITS] 1
INNER JOIN PEOPLE p ON p.PERSON_CODE = 1.PERSON_CODE
INNER JOIN AIMS la on la.person_code = 1.PERSON_CODE
WHERE la.AIM = 'Delta'
),
cte2 AS
(
SELECT p.PERSON_CODE,FES_UINS_INSTANCE_CODE
FROM [ebslive].[dbo].[PEOPLE_UNITS] 1
INNER JOIN dbo.PEOPLE p ON p.PERSON_CODE = 1.PERSON_CODE
INNER JOIN dbo.PEOPLE_UIO PUIO ON 1.UIO_ID = puio.UIO_ID
INNER JOIN dbo.LEARNER_AIMS la on la.person_code = 1.PERSON_CODE
INNER JOIN dbo.UNIT_INSTANCE_OCCURRENCES UIO ON UIO.UIO_ID = la.UIO_ID
INNER JOIN dbo.UNIT_INSTANCES UI ON UI.FES_UNIT_INSTANCE_CODE = uio.FES_UINS_INSTANCE_CODE
)

THis will do it:
Select PERSON_CODE from cte a where exists
(
select 1 from cte2 b where a.PERSON_CODE = b.PERSON_CODE
)

Related

How can I efficiently use join and pivot in my SQL code

I have 3 tables. The query returned the desired result just the sorting of records. I added Order By but it did not work.
Result should be:
I got the result it is just the sorting of records. I want to order by the ID but it is not working.
QUERY:
WITH NAMES AS (
SELECT
P.NAMES,
P.CODE,
Q.NUM_TYP,
Q.PHONE_NUM
FROM
dbo.NAMES P
INNER JOIN dbo.PHONE Q
ON P.ID = Q.ID
LEFT JOIN DBO.ADDRESS S
ON P.PRSN_IK = S.PRSN_IK
WHERE S.ADDR Is Null
)
SELECT *
FROM
NAMES
PIVOT (Max(PHONE_NUM) FOR NUM_TYP IN (WORK, HOME)) R;
Appreciate any input. Thanks.
try trhis :
select f1.Name, nullif(f1.code, '') Code ,
isnull(f2.phone_num, 'N/A') work_phone_num, isnull(f3.phone_num, 'N/A') home_phone_num
from Names f1
left outer join Phone f2 on f1.id=f2.id and f2.Num_type='WORK'
left outer join Adress f2b on f2.id=f2b.id and f2.num_type=f2b.add_type
left outer join Phone f3 on f1.id=f3.id and f3.Num_type='HOME'
left outer join Adress f3b on f3.id=f3b.id and f3.num_type=f3b.add_type
where f2b.id is null or f3b.id is null
given that your query is working, this should work :
;WITH NAMES AS (
SELECT
P.NAMES,
P.CODE,
Q.NUM_TYP,
Q.PHONE_NUM
FROM dbo.NAMES P
INNER JOIN dbo.PHONE Q
ON P.ID = Q.ID
LEFT JOIN DBO.ADDRESS S
ON P.PRSN_IK = S.PRSN_IK
WHERE S.ADDR Is Null
), PIVOTED
AS
(
SELECT *
FROM NAMES
PIVOT (Max(PHONE_NUM) FOR NUM_TYP IN (WORK, HOME)) R
)
SELECT * FROM PIVOTED piv
inner join [dbo].[NAMES] nam
on piv.names = nam.names
ORDER BY nam.ID
I have included P.ID and wrapped everything under subquery.

Inserting into new Table getting more records, CROSS JOIN, UPDATE

In my current data structure my OFFENSE table doesnt have all the columns that I need. For this reason I inner join it with several other table columns and insert it into a new table called TexasCCHPublicRecords created by me. This is my query:
INSERT INTO TexasCCHPublicRecords (OFF_IDN, TRS_IDN, AGY_TXT, DOO_DTE, AON_COD, AOL_TXT, LDA_CODE, GOC_COD, ADN_COD, ADD_TXT, ADA_DTE, REF_TXT,
IPN_NBR, ICA_NBR, DMV_COD, TRS_CODE, TRN_CODE, PERSON_ID, FIRST_NAME, LAST_NAME, DATE_OF_BIRTH, CDN, OffenseCode, OffenseName, CDNCode, ArrestingAgency,
ArrestingAgencyORI, ProsecutionAgency, ProsecutionAgencyORI)
SELECT o.* , trs.TRS_COD as 'TRS_CODE', trn.TRN_NBR as 'TRN_CODE', p.PER_IDN as 'PERSON_ID', nam.FNA_TXT as 'FIRST_NAME', nam.LNA_TXT as 'LAST_NAME',
birth.DOB_DTE as 'DATE_OF_BIRTH', cdnCode.CDN_VAL_TXT as 'CDN', offenseCode.OFF_COD as 'OffenseCode', offenseCode.LIT_TXT as 'OffenseName',
cdnCode.CDN_VAL_COD as 'CDNCode', arrestingAgency.ATR_TXT as 'ArrestingAgency', arrestingAgency.ORI_TXT as 'ArrestingAgencyORI',
prosecutionAgency.ATR_TXT as 'ProsecutionAgency',prosecutionAgency.ORI_TXT as 'ProsecutionAgencyORI'
FROM OFFENSE o
inner join CCH_PUBLIC.dbo.TRS trs on trs.TRS_IDN = o.TRS_IDN
inner join CCH_PUBLIC.dbo.TRN trn on trn.TRN_IDN = trs.TRN_IDN
inner join CCH_PUBLIC.dbo.PERSON p on p.IND_IDN = trn .IND_IDN
inner join CCH_PUBLIC.dbo.NAME nam on nam.PER_IDN = p.PER_IDN
inner join CCH_PUBLIC.dbo.BRTHDATE birth on birth.PER_IDN = p.PER_IDN
inner join CCH_PUBLIC.dbo.PROSECUTION prose on prose.TRS_IDN = o.TRS_IDN
inner join CCH_PUBLIC.dbo.AGENCY arrestingAgency on arrestingAgency.ORI_TXT = o.AGY_TXT
inner join CCH_PUBLIC.dbo.AGENCY prosecutionAgency on prosecutionAgency.ORI_TXT = o.REF_TXT
inner join CCH_PUBLIC.dbo.CRT_STAT crtStat on crtStat.TRS_IDN = o.TRS_IDN
inner join CCH_PUBLIC.dbo.CDN_COD cdnCode on cdnCode.CDN_VAL_COD = crtStat.CDN_COD
inner join CCH_PUBLIC.dbo.OFF_CODE offenseCode on offenseCode.OFF_COD = o.AON_COD
I would conclude that this table would select every offense in the OFFENSE table inner join it with the other tables and insert it into the TexasCCHPublicRecords
However after running this simple count
select count(*) as 'Offense Table Record Count' FROM OFFENSE
select count(*) as 'CCHPublicRecords Table Record Count' FROM TexasCCHPublicRecords
I end with these results:
Offense Table Record Count
11372377
CCHPublicRecords Table Record Count
49666836
There are 38 million more records in my new table. How did this happen? Is my query inserting repeated instances of the same offense row?
My goal is to SELECT an OFFENSE inner join it with the tables that are associated with it and INSERT that into my empty table. What am i doing wrong?
UPDATE
After reading one of the comments I realized that one of the tables was giving me 7 columns. Now I am trying to ONLY select the FIRST result. I am trying to do a CROSS APPLY however I am not sure what to place on the outside of the cross apply. This is my select Query:
SELECT o.*, trs.TRS_COD as 'TRS_CODE', trn.TRN_NBR as 'TRN_CODE', p.PER_IDN as 'PERSON_ID', nam.FNA_TXT as 'FIRST_NAME', nam.LNA_TXT as 'LAST_NAME',
birth.DOB_DTE as 'DATE_OF_BIRTH', cdnCode.CDN_VAL_TXT as 'CDN', offenseCode.OFF_COD as 'OffenseCode', offenseCode.LIT_TXT as 'OffenseName',
cdnCode.CDN_VAL_COD as 'CDNCode', arrestingAgency.ATR_TXT as 'ArrestingAgency', arrestingAgency.ORI_TXT as 'ArrestingAgencyORI',
prosecutionAgency.ATR_TXT as 'ProsecutionAgency',prosecutionAgency.ORI_TXT as 'ProsecutionAgencyORI'
FROM OFFENSE o
inner join CCH_PUBLIC.dbo.TRS trs on trs.TRS_IDN = o.TRS_IDN
inner join CCH_PUBLIC.dbo.TRN trn on trn.TRN_IDN = trs.TRN_IDN
inner join CCH_PUBLIC.dbo.PERSON p on p.IND_IDN = trn.IND_IDN
inner join CCH_PUBLIC.dbo.BRTHDATE birth on birth.PER_IDN = p.PER_IDN
inner join CCH_PUBLIC.dbo.PROSECUTION prose on prose.TRS_IDN = o.TRS_IDN
inner join CCH_PUBLIC.dbo.AGENCY arrestingAgency on arrestingAgency.ORI_TXT = o.AGY_TXT
inner join CCH_PUBLIC.dbo.AGENCY prosecutionAgency on prosecutionAgency.ORI_TXT = o.REF_TXT
inner join CCH_PUBLIC.dbo.CRT_STAT crtStat on crtStat.TRS_IDN = o.TRS_IDN
inner join CCH_PUBLIC.dbo.CDN_COD cdnCode on cdnCode.CDN_VAL_COD = crtStat.CDN_COD
inner join CCH_PUBLIC.dbo.OFF_CODE offenseCode on offenseCode.OFF_COD = o.AON_COD
CROSS APPLY (
SELECT TOP 1 *
FROM CCH_PUBLIC.dbo.NAME as nam
WHERE nam.PER_IDN = p.PER_IDN
) nam
is the nam out of the CROSS APPLY correct?

How to rewrite legacy join syntax *= in SQL Server

I am trying to rewrite legacy join syntax with new standards.
SELECT count(*)
FROM es_dbo.tablTypes t
,es_dbo.tablReg r
,es_dbo.tabl_PRGandCLI p
WHERE t.ClientType *= r.ClientType
AND p.ID IN (
SELECT DISTINCT ClientID
FROM esinet_dbo.tablReG
)
AND t.ClientType IN (#intClientType)
Here is what I am trying.
SELECT count(*)
FROM es_dbo.tablTypes t
LEFT JOIN es_dbo.tablReg r ON t.ClientType = r.ClientType
LEFT JOIN es_dbo.tabl_PRGandCLI p ON p.ID IN (
SELECT DISTINCT ClientID
FROM es_dbo.tablReG
)
I am getting same no of records whether I use LEFT JOIN or INNER JOIN in 2nd part of query. Can anyone explain
Try the following:
SELECT count(*)
FROM es_dbo.tablTypes t
left join es_dbo.tablReg r on t.ClientType = r.ClientType
WHERE t.ClientType IN (#intClientType)
EXISTS (SELECT 1 FROM esinet_dbo.tablReG p WHERE r.ClientID = p.ID)
1) I assumed #intClientType is a scalar value, so no need for IN
2) removed DISTINCT and subquery as you check for existence. EXISTS should be faster as it involves finding the first element, rather than doing some sorting for DISTINCT.
3) *= was replaced with LEFT JOIN, based on discussion from here.
It is neither inner join nor left join according to query it seems like cross join so you can use following query:
SELECT count(*)
FROM es_dbo.tablTypes t
LEFT JOIN es_dbo.tablReg r ON t.ClientType = r.ClientType,
es_dbo.tabl_PRGandCLI p WHERE p.ID IN (
SELECT DISTINCT ClientID
FROM es_dbo.tablReG
)

Select only columns from joined tables from CTE

The following is my CTE:
;WITH CTE AS
(SELECT O.*, E.Num, E.Amount
FROM OData O
INNER JOIN Equip E
ON O.Name = E.Name)
SELECT * FROM CTE -- gives results I want to join to
The following is the query that I want to SELECT from (and only use this SELECT statement for my query results:
SELECT
MU.Type
,MU.Num
,MU.MTBUR
,MF.MTBF
,MU.Hours
,MF.Hours
FROM
MUType_Stage MU
INNER JOIN
MFType_Stage MF
ON
MU.Type = MF.Type
AND
MU.Num = MF.Num
-- Need do JOIN to CTE right here
INNER JOIN
Status_STAGE S
ON
MU.Nu = S.Part
LEFT OUTER JOIN
RCN N
ON
N.Name = R.Part
LEFT OUTER JOIN
Repair RR
ON
R.ACSS_Name = RR.Name
So basically I need to JOIN to the CTE inside the SELECT query in which I want the results.
OR ALTERNATIVELY Uses this select statement to join to the CTE but only what the selected columns from the second select statement
Try this syntax
WITH CTE
AS (SELECT O.*,
E.Num,
E.Amount
FROM OData O
INNER JOIN Equip E
ON O.Name = E.Name)
SELECT MU.Type,
MU.Num,
MU.MTBUR,
MF.MTBF,
MU.Hours,
MF.Hours
FROM MUType_Stage MU
INNER JOIN MFByACType_Stage MF
ON MU.Type = MF.Type
AND MU.Num = MF.Num
INNER JOIN CTE C --- JOIN HERE as like other tables
ON C.Num = MF.Num
INNER JOIN Status_STAGE S
ON MU.Nu = S.Part
LEFT OUTER JOIN RCN N
ON N.Name = R.Part
LEFT OUTER JOIN Repair RR
ON R.ACSS_Name = RR.Name

Get Max(id) from one to many table

I know this question was asked many times but I was tring and trying without success
I have one to many relationship between two tables and some more inner-joins to get more data.
Here is my query:
SELECT
ShopOffer.OfferID,
ShopOffer.OfferMessage,
Shop.ID,
Shop.Name,
Shop.Phone,
[User].Name,
[User].UserID,
ShopOfferStatus.Name AS StatusName,
BlockedShopInUser.IsBlocked
FROM
ShopOffer
INNER JOIN ShopOfferStatus ON ShopOffer.ShopOfferStatusID = ShopOfferStatus.ShopOfferStatusID
INNER JOIN Shop ON ShopOffer.ShopID = Shop.ShopID
INNER JOIN UserRequest ON ShopOffer.UserRequestID = UserRequest.UserRequestID
INNER JOIN [User] ON UserRequest.UserID = [User].UserID
INNER JOIN BlockedShopInUser ON Shop.ShopID = BlockedShopInUser.ShopID AND [User].UserID = BlockedShopInUser.UserID
Each shop can create many offers. In that query I would like to get only the last offer for each shop.
Thanks.
Here is a way:
;WITH LastShopOffer AS
(
SELECT *,
RN = ROW_NUMBER() OVER(PARTITION BY ShopID ORDER BY OfferID DESC)
FROM ShopOffer
)
SELECT
SO.OfferID,
SO.OfferMessage,
S.ID,
S.Name,
S.Phone,
U.Name,
U.UserID,
SOS.Name AS StatusName,
B.IsBlocked
FROM ( SELECT *
FROM LastShopOffer
WHERE RN = 1) SO
INNER JOIN ShopOfferStatus SOS
ON SO.ShopOfferStatusID = SOS.ShopOfferStatusID
INNER JOIN Shop S
ON SO.ShopID = S.ShopID
INNER JOIN UserRequest UR
ON SO.UserRequestID = UR.UserRequestID
INNER JOIN [User] U
ON UR.UserID = U.UserID
INNER JOIN BlockedShopInUser B
ON S.ShopID = B.ShopID
AND U.UserID = B.UserID;
I think you have to start with Shop and then perform a CROSS APPLY on the TOP 1 record from ShopOffer:
SELECT
ShopOffer.OfferID,
ShopOffer.OfferMessage,
Shop.ID,
Shop.Name,
Shop.Phone,
[User].Name,
[User].UserID,
ShopOfferStatus.Name AS StatusName,
BlockedShopInUser.IsBlocked
FROM Shop
CROSS APPLY (
SELECT TOP 1 OfferID, OfferMessage, ShopOfferStatusID, UserRequestID
FROM ShopOffer AS s
WHERE s.ShopID = Shop.ShopID
ORDER BY s.OfferID DESC
) ShopOffer
INNER JOIN ShopOfferStatus ON ShopOffer.ShopOfferStatusID = ShopOfferStatus.ShopOfferStatusID
INNER JOIN UserRequest ON ShopOffer.UserRequestID = UserRequest.UserRequestID
INNER JOIN [User] ON UserRequest.UserID = [User].UserID
INNER JOIN BlockedShopInUser ON Shop.ShopID = BlockedShopInUser.ShopID AND [User].UserID = BlockedShopInUser.UserID

Resources