0
下面是一個包含3個表的示例模式。我試圖運行一個查詢,返回所有子班次都是狀態6的所有作業。如果作業有一個狀態爲5的子班次,則不應返回作業。來自下面插入的示例數據的查詢的正確響應是沒有行返回。將PostgreSQL子查詢轉換爲連接
下面有一個工作查詢,註釋「Works」。我試圖重構「作品」查詢使用連接而不是子查詢。評論「不工作」的查詢是我的嘗試。
-- begin setup and table creation: only run this section once.
CREATE EXTENSION "uuid-ossp";
CREATE TABLE jobs
(
id uuid NOT NULL DEFAULT uuid_generate_v4(),
CONSTRAINT jobs_pkey PRIMARY KEY (id)
);
CREATE TABLE bookings
(
id uuid NOT NULL DEFAULT uuid_generate_v4(),
job_id uuid,
CONSTRAINT bookings_pkey PRIMARY KEY (id)
);
CREATE TABLE shifts
(
id uuid NOT NULL DEFAULT uuid_generate_v4(),
booking_id uuid,
status integer,
CONSTRAINT shifts_pkey PRIMARY KEY (id)
);
insert into jobs (id) values ('e857c86c-bc31-11e6-9aae-57793f585d49');
insert into bookings (id, job_id) values ('736da82c-bc32-11e6-b9b8-f36753d321ac', 'e857c86c-bc31-11e6-9aae-57793f585d49');
insert into bookings (id, job_id) values ('7d839e5c-bc32-11e6-8bb3-4fa95be86a74', 'e857c86c-bc31-11e6-9aae-57793f585d49');
insert into shifts (booking_id, status) values ('736da82c-bc32-11e6-b9b8-f36753d321ac', 6);
insert into shifts (booking_id, status) values ('7d839e5c-bc32-11e6-8bb3-4fa95be86a74', 5);
-- end setup and table creation
我們希望所有孩子的變化是狀態6.所有作業如果作業具有爲5的狀態的孩子轉變,作業應不予退還。上面插入的示例數據對查詢的正確響應是不返回行。
不工作:(
SELECT "jobs".*
FROM "jobs"
inner join bookings b1 on jobs.id = b1.job_id
inner join shifts s1 on b1.id = s1.booking_id
left outer join bookings b2 on jobs.id = b2.job_id
left outer join shifts s2 on b2.id = s2.booking_id and s2.status IN (2,3,4,5)
WHERE s1.status = 6
AND s2.id IS NULL
GROUP BY "jobs"."id";
作品
SELECT "jobs".*
FROM "jobs"
WHERE jobs.id IN (
SELECT job_id
FROM bookings
WHERE bookings.id IN (
SELECT booking_id FROM shifts WHERE status = 6
)
) AND jobs.id NOT IN (
SELECT job_id FROM bookings WHERE bookings.id IN (
SELECT booking_id FROM shifts WHERE status IN (2,3,4,5)
)
)
GROUP BY "jobs"."id";
我如何重構「作品」查詢,使用聯接,而不是子查詢呢?「不工作」的查詢是我的嘗試。
你的子查詢方法有什麼問題?子查詢似乎沒有關聯,所以從性能角度來看,它們可能不是一個大問題。 –
連接不一定會返回與子查詢解決方案相同的結果。那麼你爲什麼要重寫呢? –
您可能來自mysql後臺,其中子查詢幾乎總是比連接慢。在postgresql中並非如此。 **你不需要這樣做** – e4c5