TSQL 2008 Running total with previous months & years - tsql

I'm trying to get the Running total from the values from the previous months. And if the month is january I would like to get the total from the previous year and so forth.
I hope someone can help.
WITH CTE AS (SELECT COUNT(LZP.pv_zaaknummer) AS [Aantal LZP]
, YEAR(LZP.lzp_actief_vanaf) AS Jaar
, MONTH(LZP.lzp_actief_vanaf) AS Maand
FROM dm.crm_LZP_Vn_zaaktype_leefzorgplan_registrerenExtensionBase_hist AS LZP
WHERE LZP.LZP_actief_tot_LDTS > GETDATE()
GROUP BY YEAR(LZP.lzp_actief_vanaf)
, MONTH(LZP.lzp_actief_vanaf)
)
SELECT a.Jaar
, a.Maand
, a.[Aantal LZP]
, (
SELECT SUM(b.[Aantal LZP])
FROM CTE AS b
WHERE b.Jaar <= a.Jaar
) AS [Running Total 1]
, (
SELECT SUM(b.[Aantal LZP])
FROM CTE AS b
WHERE b.Jaar <= a.Jaar
AND b.Maand <= a.Maand
) AS [Running Total 2]
FROM CTE AS a
ORDER BY a.Jaar, a.Maand;
Results as of now, I'm getting the Totals per year and then the running totals per year:
Jaar Maand Aantal LZP Running Total 1 Running Total 2
2014 4 11 661 11
2014 5 52 661 63
2014 6 70 661 133
2014 7 76 661 209
2014 8 39 661 248
2014 9 86 661 334
2014 10 112 661 446
2014 11 120 661 566
2014 12 95 661 661
2015 1 57 3327 57
2015 2 109 3327 166
2015 3 196 3327 362
2015 4 200 3327 573
2015 5 169 3327 794
2015 6 233 3327 1097
2015 7 276 3327 1449
2015 8 224 3327 1712
2015 9 203 3327 2001
2015 10 291 3327 2404
2015 11 296 3327 2820
2015 12 412 3327 3327
2016 1 311 6062 368
2016 2 341 6062 818
2016 3 476 6062 1490
2016 4 440 6062 2141
2016 5 418 6062 2780
2016 6 500 6062 3583
2016 7 249 6062 4184
I would like it to be:
Running Total 3
11
63
133
209
248
334
446
566
661
718
827
1023
1223
1392
1625
1901
2125
2328
2619
2915
3327
3638
3979
4455
4895
5313
5813
6062

you could do it without subquery try
....................)
SELECT a.Jaar
, a.Maand
, a.[Aantal LZP],SUM([Aantal LZP]) over (order by jaar) [Running Total 1]
, SUM([Aantal LZP]) over (partition by jaar order by maand) [Running Total 2],
SUM([Aantal LZP]) over ( order by jaar,maand) [Running Total 3]
FROM CTE AS a
ORDER BY a.Jaar, a.Maand;
old version
SELECT a.Jaar
, a.Maand
, a.[Aantal LZP],(SELECT SUM(b.[Aantal LZP])
FROM CTE AS b
WHERE b.Jaar <= a.Jaar
) [Running Total 1],
(SELECT SUM(b.[Aantal LZP])
FROM CTE AS b
WHERE b.Jaar <= a.Jaar and Maand<=a.Maand
) [Running Total 2]
, (SELECT SUM(b.[Aantal LZP])
FROM CTE AS b
WHERE dateadd(year,jaar-1900,dateadd(month,maand-1,0)) <= dateadd(year,a.jaar-1900,dateadd(month,a.maand-1,0))
) [Running Total 3]
FROM CTE AS a
ORDER BY a.Jaar, a.Maand;

Found the Solution but now I must find to integrate it so it responds to my reportparameters Jaar and Maand
DECLARE #SalesTbl TABLE (Jaar int, Maand int, Aantal int, RunningTotal int)
DECLARE #Jaar int,
#Maand int,
#Aantal int,
#RunningTotal int
SET #RunningTotal = 0
DECLARE rt_cursor CURSOR
FOR
WITH CTE AS
(SELECT COUNT(LZP.pv_zaaknummer) AS [Aantal LZP]
, YEAR(LZP.lzp_actief_vanaf) AS Jaar
, MONTH(LZP.lzp_actief_vanaf) AS Maand
FROM dm.crm_LZP_Vn_zaaktype_leefzorgplan_registrerenExtensionBase_hist AS LZP
WHERE LZP.LZP_actief_tot_LDTS > GETDATE()
GROUP BY LZP.lzp_actief_vanaf
)
SELECT A.Jaar, A.Maand, SUM(A.[Aantal LZP])
FROM CTE AS A
GROUP BY Jaar, Maand
ORDER BY A.Jaar, A.Maand
OPEN rt_cursor
FETCH NEXT FROM rt_cursor INTO #Jaar, #Maand, #Aantal
WHILE ##FETCH_STATUS = 0
BEGIN
SET #RunningTotal = #RunningTotal + #Aantal
INSERT #SalesTbl VALUES (#Jaar, #Maand,#Aantal,#RunningTotal)
FETCH NEXT FROM rt_cursor INTO #Jaar, #Maand, #Aantal
END
CLOSE rt_cursor
DEALLOCATE rt_cursor
SELECT * FROM #SalesTbl

Related

TSQL Select TOP and Distinct from one table into a TEMP table

I have the following table:
Data nr1 nr2 nr3 nr4 nr5 nr6
2020-09-12 6 15 36 42 67 78
2020-09-10 46 48 67 78 80 87
2020-09-08 23 27 28 31 69 89
2020-09-05 7 14 27 56 72 83
2020-09-03 16 17 38 39 68 84
2020-09-01 10 22 28 45 48 71
2020-08-29 1 3 35 42 55 61
2020-08-27 37 49 52 53 75 87
2020-08-25 15 24 31 70 83 84
2020-08-22 7 12 45 47 73 87
2020-08-20 7 17 30 39 41 67
2020-08-18 13 22 28 58 65 77
2020-08-17 5 9 26 62 77 79
2020-08-13 4 5 49 57 66 75
2020-08-11 7 9 38 68 78 80
2020-08-08 6 16 22 55 58 83
2020-08-06 21 37 40 46 69 80
2020-08-04 5 19 21 25 45 82
2020-08-01 4 14 17 18 26 45
2020-07-30 4 15 19 26 28 55
2020-07-28 23 45 49 71 80 82
2020-07-25 18 30 42 70 78 80
2020-07-23 10 29 37 49 56 57
2020-07-21 4 34 46 54 55 62
2020-07-18 18 33 49 76 80 84
I have to do the following task:
Select into a #TEMP table with only one column DistinctNumbers all distinct numbers of the above table because some numbers in the above table might be repeated across rows and columns.
Select into another #TEMP table all numbers in the range from 1 to 99 which are not in the original table.
What is the best way of accomplishing these two tasks?
You should unpivot original table first
1.Unpivot original table into #temp table
2.Now you have all numbers in one column
3.Use while between 1 and 99 and insert counter into #RESULT table where not in #temp(unpivoted table)
SELECT DISTINCT(num) num INTO #TEMP_DISTINCT_NUMBERS FROM ORIGINAL_TABLE UNPIVOT (
num
FOR PivotColumn IN (nr1,nr2,nr3,nr4,nr5,nr6)
) AS UNPIVOTE_TABLE
CREATE TABLE #RESULT(NUM INT)
DECLARE #COUNTER INT =1;
WHILE(#COUNTER<=99)
BEGIN
INSERT INTO #RESULT SELECT #COUNTER WHERE #COUNTER NOT IN (SELECT num FROM
#TEMP_DISTINCT_NUMBERS)
SET #COUNTER=#COUNTER+1
END
SELECT * FROM #RESULT
you can try this:
;WITH tally
AS (SELECT 1 AS num
UNION ALL
SELECT num + 1
FROM tally
WHERE num < 99)
SELECT DISTINCT tally.num
FROM tally
LEFT JOIN
( SELECT num FROM #dataset --your dataset
CROSS APPLY (VALUES (nr1),(nr2),(nr3),(nr4),(nr5),(nr6)) AS B (num)
) AS dataset
ON tally.num = dataset.num
WHERE dataset.num IS NULL
Code above:
Create [tally] recursive common table expression with sequence from 1 to 99
Left join tally with your unpivoted dataset ...
test here: https://rextester.com/YEB57637

Including all months for the year without duplicates when date ranges can be consecutive or not using T-SQL

I have one or more start and end periods which can be consecutive, overlap, or anything in between. My goal is to have all 12 months displayed regardless of when the period starts; that is, I can see months before the period, during the period and potentially after the period. For sake of this example, I'm checking it against 2019 so I want to see all 12 months filled in for 2019.
I have the following sample data to illustrate the problem:
DECLARE #DATES TABLE (ID int, EffectiveDate date, EffectiveEndDate date)
INSERT INTO #DATES
VALUES
(43, '2018-10-01', '2019-09-30'),
(43, '2019-10-01', '2020-09-30'),
(44, '2019-10-01', '2020-09-30');
I also have a "tally" table which has all 12 months and the start of the month (omitted for brevity but it's a temp table with a column called N which has a value of 1-12 representing the month, and a column StartOfMonth which is the start date of the month. Now what I want is to have each ID (43 and 44 in this case) show all 12 months. This is easy with 43 where there are two records that run from October 2018 to November 2020, as it falls within all 12 months. 44 however only gives me October, November and December since there is only one row that begins in October. I cannot add a row for the previous months.
The Months table is simply defined as the follows:
DROP TABLE IF EXISTS #Months;
CREATE TABLE #Months (N tinyint, StartOfMonth date);
INSERT INTO #Months
VALUES
(1, DATEFROMPARTS(2019, 1, 1)),
(2, DATEFROMPARTS(2019, 2, 1)),
(3, DATEFROMPARTS(2019, 3, 1)),
(4, DATEFROMPARTS(2019, 4, 1)),
(5, DATEFROMPARTS(2019, 5, 1)),
(6, DATEFROMPARTS(2019, 6, 1)),
(7, DATEFROMPARTS(2019, 7, 1)),
(8, DATEFROMPARTS(2019, 8, 1)),
(9, DATEFROMPARTS(2019, 9, 1)),
(10, DATEFROMPARTS(2019, 10, 1)),
(11, DATEFROMPARTS(2019, 11, 1)),
(12, DATEFROMPARTS(2019, 12, 1));
Code:
SELECT Month = m.N,
d.ID,
d.EffectiveDate,
d.EffectiveEndDate,
-- This flag doesn't mean anything, just so I can better see the results I'm getting
Ind = CASE
WHEN m.StartOfMonth BETWEEN d.EffectiveDate AND d.EffectiveEndDate
THEN 1
ELSE 0
END
FROM #dates d
LEFT JOIN #Months m
ON m.N BETWEEN 1 AND 12
WHERE
m.StartOfMonth
BETWEEN EffectiveDate AND EffectiveEndDate
ORDER BY ID, m.N;
This gives me the following (wrong) output:
Month ID EffectiveDate EffectiveEndDate Ind
1 43 2018-10-01 2019-09-30 1
2 43 2018-10-01 2019-09-30 1
3 43 2018-10-01 2019-09-30 1
4 43 2018-10-01 2019-09-30 1
5 43 2018-10-01 2019-09-30 1
6 43 2018-10-01 2019-09-30 1
7 43 2018-10-01 2019-09-30 1
8 43 2018-10-01 2019-09-30 1
9 43 2018-10-01 2019-09-30 1
10 43 2019-10-01 2020-09-30 1
11 43 2019-10-01 2020-09-30 1
12 43 2019-10-01 2020-09-30 1
!!! THIS PART IS WRONG !!!
10 44 2019-10-01 2020-09-30 1
11 44 2019-10-01 2020-09-30 1
12 44 2019-10-01 2020-09-30 1
If I skip the effective date/effective end date check or try to do some sort of case statement where I say if month begins before the effective date then include it anyway 43 doubles up on the months because there are two rows, while 44 works as expected.
What I need is to get this:
Month ID EffectiveDate EffectiveEndDate Ind
1 43 2018-10-01 2019-09-30 1
2 43 2018-10-01 2019-09-30 1
3 43 2018-10-01 2019-09-30 1
4 43 2018-10-01 2019-09-30 1
5 43 2018-10-01 2019-09-30 1
6 43 2018-10-01 2019-09-30 1
7 43 2018-10-01 2019-09-30 1
8 43 2018-10-01 2019-09-30 1
9 43 2018-10-01 2019-09-30 1
10 43 2019-10-01 2020-09-30 1
11 43 2019-10-01 2020-09-30 1
12 43 2019-10-01 2020-09-30 1
1 44 2019-10-01 2020-09-30 0
2 44 2019-10-01 2020-09-30 0
3 44 2019-10-01 2020-09-30 0
4 44 2019-10-01 2020-09-30 0
5 44 2019-10-01 2020-09-30 0
6 44 2019-10-01 2020-09-30 0
7 44 2019-10-01 2020-09-30 0
8 44 2019-10-01 2020-09-30 0
9 44 2019-10-01 2020-09-30 0
10 44 2019-10-01 2020-09-30 1
11 44 2019-10-01 2020-09-30 1
12 44 2019-10-01 2020-09-30 1
where all 12 months are showing for all situations, whether there's consecutive ranges or one range that starts at any given point in the year.
There's probably a better way to do this, but here is an ugly solution:
-- Build base data
DECLARE #DATES TABLE (ID int, EffectiveDate date, EffectiveEndDate date)
INSERT INTO #dates
VALUES
(43, '2018-10-01', '2019-09-30'),
(43, '2019-10-01', '2020-09-30'),
(44, '2019-10-01', '2020-09-30');
DECLARE #months TABLE (StartOfMonth date, n int)
;WITH dateCTE
AS
(
SELECT ROW_NUMBER() OVER (ORDER BY number) - 1 AS rn
FROM master.dbo.spt_values
)
INSERT #months (StartOfMonth, n)
SELECT CAST(DATEADD(mm, rn, '2018-01-01') AS date) AS StartOfMonth, DATEPART(mm,DATEADD(mm, rn, '2018-01-01')) AS n
FROM dateCTE
WHERE rn < 48
-- build a list of all IDs and months where the ID is active in the year
;with dateCTE
AS
(
SELECT DISTINCT d.ID, m.StartOfMonth, m.n
FROM #months AS m
CROSS
JOIN #dates AS d
WHERE DATEPART(YEAR,m.StartOfMonth) BETWEEN DATEPART(YEAR,d.EffectiveDate) and DATEPART(YEAR,d.EffectiveEndDate)
)
-- join list from previous step to the activity data
-- this generates the full list with NULLs where the ID was not active
,listCTE
AS
(
SELECT cd.ID, cd.StartOfMonth, cd.n, d.EffectiveDate, d.EffectiveEndDate
FROM dateCTE AS cd
LEFT
JOIN #dates AS d
ON d.ID = cd.ID
AND cd.StartOfMonth between d.EffectiveDate AND d.EffectiveEndDate
)
-- fill in the NULLS by joining the table back to itelf
SELECT n AS [Month],
ID,
COALESCE(EffectiveDate,
(SELECT TOP 1 EffectiveDate FROM listCTE AS l2 WHERE l2.ID = l.ID AND l2.EffectiveDate > l.StartOfMonth ORDER BY l2.StartOfMonth DESC),
(SELECT TOP 1 EffectiveDate FROM listCTE AS l2 WHERE l2.ID = l.ID AND l2.EffectiveEndDate < l.StartOfMonth ORDER BY l2.StartOfMonth DESC)
) AS EffectiveDate,
COALESCE(EffectiveEndDate,
(SELECT TOP 1 EffectiveEndDate FROM listCTE AS l2 WHERE l2.ID = l.ID AND l2.EffectiveDate > l.StartOfMonth ORDER BY l2.StartOfMonth DESC),
(SELECT TOP 1 EffectiveEndDate FROM listCTE AS l2 WHERE l2.ID = l.ID AND l2.EffectiveEndDate < l.StartOfMonth ORDER BY l2.StartOfMonth DESC)
) AS EffectiveEndDate,
CASE
WHEN StartOfMonth BETWEEN EffectiveDate AND EffectiveEndDate
THEN 1
ELSE 0
END AS Ind,
StartOfMonth
FROM listCTE AS l
WHERE DATEPART(YEAR,StartOfMonth) = 2019
ORDER BY ID, StartOfMonth
(This code uses a #months table variable rather than the #months temp table in the original)
This works by building a list of all IDs and months, then left-joining that to the #dates table to generate the months where each ID is active. Finally, the second result set is joined back to itself to fill in the NULLs.
This is likely to have horrible performance when applied to data at scale; it might be possible to mitigate this by materialising the interim steps of the CTEs into tables (or temp tables) with appropriate indexes.

PostgreSQL - filter function for dates

I am trying to use the built-in filter function in PostgreSQL to filter for a date range in order to sum only entries falling within this time-frame.
I cannot understand why the filter isn't being applied.
I am trying to filter for all product transactions that have a created_at date of the previous month (so in this case that were created in June 2017).
SELECT pt.created_at::date, pt.customer_id,
sum(pt.amount/100::double precision) filter (where (date_part('month', pt.created_at) =date_part('month', NOW() - interval '1 month') and
date_part('year', pt.created_at) = date_part('year', NOW()) ))
from
product_transactions pt
LEFT JOIN customers c
ON c.id= pt.customer_id
GROUP BY pt.created_at::date,pt.customer_id
Please find my expected results (sum of the amount for each day in the previous month - for each customer_id if an entry for that day exists) and the actual results I get from the query - below (using date_trunc).
Expected results:
created_at| customer_id | amount
2017-06-30 1 220.5
2017-06-28 15 34.8
2017-06-28 12 157
2017-06-28 48 105.6
2017-06-27 332 425.8
2017-06-25 1 58.0
2017-06-25 23 22.5
2017-06-21 14 88.9
2017-06-17 2 34.8
2017-06-12 87 250
2017-06-05 48 135.2
2017-06-05 12 95.7
2017-06-01 44 120
Results:
created_at| customer_id | amount
2017-06-30 1 220.5
2017-06-28 15 34.8
2017-06-28 12 157
2017-06-28 48 105.6
2017-06-27 332 425.8
2017-06-25 1 58.0
2017-06-25 23 22.5
2017-06-21 14 88.9
2017-06-17 2 34.8
2017-06-12 87 250
2017-06-05 48 135.2
2017-06-05 12 95.7
2017-06-01 44 120
2017-05-30 XX YYY
2017-05-25 XX YYY
2017-05-15 XX YYY
2017-04-30 XX YYY
2017-03-02 XX YYY
2016-11-02 XX YYY
The actual results give me the sum for all dates in the database, so no date time-frame is being applied in the query for a reason I cannot understand. I'm seeing dates that are both not for June 2017 and also from previous years.
Use date_trunc(..) function:
SELECT pt.created_at::date, pt.customer_id, c.name,
sum(pt.amount/100::double precision) filter (where date_trunc('month', pt.created_at) = date_trunc('month', NOW() - interval '1 month'))
from
product_transactions pt
LEFT JOIN customers c
ON c.id= pt.customer_id
GROUP BY pt.created_at::date

Flatten one column keeping others in POSTGRESQL

I created a view which is presently giving the data like this:
practice_name message_type message_count
CHC ALOG_SYNC 1
CHC BULKNT 0
CHC PIE_SYNC 1
CHC PPRV_SYNC 1
CHC SYNC_PRACT 3
CHC SYNC_PROV 9
CHC SYNC_WTXT 3
CHC SYNC_XYZ 0
Midtown ALOG_SYNC 0
Midtown BULKNT 0
Midtown PIE_SYNC 0
Midtown PPRV_SYNC 0
Midtown SYNC_PRACT 3
Midtown SYNC_PROV 0
Midtown SYNC_WTXT 3
Midtown SYNC_XYZ 0
NextGen MedicalPractice ALOG_SYNC 0
NextGen MedicalPractice BULKNT 1
NextGen MedicalPractice PIE_SYNC 0
NextGen MedicalPractice PPRV_SYNC 0
NextGen MedicalPractice SYNC_PRACT 3
NextGen MedicalPractice SYNC_PROV 591
NextGen MedicalPractice SYNC_WTXT 3
NextGen MedicalPractice SYNC_XYZ 0
My View:
CREATE OR REPLACE VIEW sha.sha_export_queue_view AS
SELECT q3.practice_name,
q3.message_type,
q3.share_site_org_key,
COALESCE(q2.message_count, '0'::text) AS message_count
FROM ( SELECT q1.practice_name,
mt.message_type,
q1.share_site_org_key
FROM sha.message_types mt,
( SELECT DISTINCT jsonb_array_elements((ai.result_json -> 'Patient Portal Operational Information'::text) -> 'nxmd_export contents by message type'::text) ->> 'Practice Name'::text AS practice_name,
ai.share_site_org_key
FROM sha.sha_share_site_view ssv
LEFT JOIN ( SELECT mytable2.assessment_id,
mytable2.result_json,
mytable2.share_site_org_key,
mytable2.rnk
FROM ( SELECT assessment_info.assessment_id,
assessment_info.result_json,
assessment_info.share_site_org_key,
dense_rank() OVER (PARTITION BY assessment_info.share_site_org_key ORDER BY assessment_info.modified_datetime DESC) AS rnk
FROM sha.assessment_info
WHERE assessment_info.assessment_id = 8::numeric) mytable2
WHERE mytable2.rnk = 1) ai ON ssv.share_site_org_key = ai.share_site_org_key) q1) q3
LEFT JOIN ( SELECT jsonb_array_elements((ai.result_json -> 'Patient Portal Operational Information'::text) -> 'nxmd_export contents by message type'::text) ->> 'Practice Name'::text AS practice_name,
jsonb_array_elements((ai.result_json -> 'Patient Portal Operational Information'::text) -> 'nxmd_export contents by message type'::text) ->> 'Message Type'::text AS message_type,
jsonb_array_elements((ai.result_json -> 'Patient Portal Operational Information'::text) -> 'nxmd_export contents by message type'::text) ->> 'Message Count'::text AS message_count
FROM sha.sha_share_site_view ssv
LEFT JOIN ( SELECT mytable2.assessment_id,
mytable2.result_json,
mytable2.share_site_org_key,
mytable2.rnk
FROM ( SELECT assessment_info.assessment_id,
assessment_info.result_json,
assessment_info.share_site_org_key,
dense_rank() OVER (PARTITION BY assessment_info.share_site_org_key ORDER BY assessment_info.modified_datetime DESC) AS rnk
FROM sha.assessment_info
WHERE assessment_info.assessment_id = 8::numeric) mytable2
WHERE mytable2.rnk = 1) ai ON ssv.share_site_org_key = ai.share_site_org_key) q2 ON q3.message_type::text = q2.message_type AND q3.practice_name = q2.practice_name
ORDER BY q3.practice_name;
I want the second column to be flattened:
Practice Time Stamp <<message type 1>> <<message type 2>> <<message type 3>> <<message type 4 >> <<message type 5>> <<message type 6>> <<message type 7>> <<message type 8>>
Practice Name 1 21-12-2016 10:00 23 25 27 29 31 33 35 37
Practice Name 2 21-12-2016 10:00 24 26 28 30 32 34 36 38
Practice Name 3 21-12-2016 13:00 25 27 29 31 33 35 37 39
Practice Name 4 21-12-2016 13:00 26 28 30 32 34 36 38 40
Practice Name 5 24-12-2016 13:00 27 29 31 33 35 37 39 41
Practice Name 6 27-12-2016 13:00 28 30 32 34 36 38 40 42
Practice Name 7 30-12-2016 13:00 29 31 33 35 37 39 41 43
Practice Name 8 02-01-2017 13:00 30 32 34 36 38 40 42 44
Practice Name 1 05-01-2017 13:00 31 33 35 37 39 41 43 45
Practice Name 2 08-01-2017 13:00 32 34 36 38 40 42 44 46
Practice Name 3 11-01-2017 13:00 33 35 37 39 41 43 45 47
Is there any way I can achieve that?
Sorry for the little alignment issue.
The values are corresponding message type values
Sample for query (idea in comments to question):
SELECT
practice_name,
sum("ALOG_SYNC") AS "ALOG_SYNC",
sum("BULKNT") AS "BULKNT",
...
FROM (
SELECT
practice_name,
CASE WHEN q3.message_type = 'ALOG_SYNC' THEN sum(message_count) END AS "ALOG_SYNC",
CASE WHEN q3.message_type = 'BULKNT' THEN sum(message_count) END AS "BULKNT"
FROM
<your from + where clause>
) AS A
GROUP BY 1
Probably your query might be optimised.
Or you can use crosstab function (https://www.postgresql.org/docs/current/static/tablefunc.html)

Using a join instead of subquery

For this question:
Get the pids of products ordered through any agent who makes at least one order for a customer in Kyoto. Use joins this time; no sub-queries.
I was able to get the answer using a subquery:
select distinct pid
from orders
where aid in (
select aid
from orders
where cid in(
select cid
from customers
where city = 'Kyoto'
)
)
I cannot figure out how to do this using only joins however.
This code returns the aid's that i need to get the pid's however i can't come up with a way to get them without using a sub query:
select distinct o.aid
from orders o, customers c
where o.cid = c.cid
and c.city = 'Kyoto'
Here are the two tables i am using:
Customers:
cid name city discount
c001 Tiptop Duluth 10.00
c002 Basics Dallas 12.00
c003 Allied Dallas 8.00
c004 ACME Duluth 8.00
c005 Weyland-Yutani Acheron 0.00
c006 ACME Kyoto 0.00
and Orders:
ordno mon cid aid pid qty dollars
1011 jan c001 a01 p01 1000 450.00
1013 jan c002 a03 p03 1000 880.00
1015 jan c003 a03 p05 1200 1104.00
1016 jan c006 a01 p01 1000 500.00
1017 feb c001 a06 p03 600 540.00
1018 feb c001 a03 p04 600 540.00
1019 feb c001 a02 p02 400 180.00
1020 feb c006 a03 p07 600 600.00
1021 feb c004 a06 p01 1000 460.00
1022 mar c001 a05 p06 400 720.00
1023 mar c001 a04 p05 500 450.00
1024 mar c006 a06 p01 800 400.00
1025 apr c001 a05 p07 800 720.00
1026 may c002 a05 p03 800 740.00