Received: from localhost (maia-5.hub.org [200.46.204.182]) by postgresql.org (Postfix) with ESMTP id 4CA119FB758 for ; Wed, 6 Jun 2007 05:34:22 -0300 (ADT) Received: from postgresql.org ([200.46.204.71]) by localhost (mx1.hub.org [200.46.204.182]) (amavisd-maia, port 10024) with ESMTP id 94927-09 for ; Wed, 6 Jun 2007 05:34:15 -0300 (ADT) X-Greylist: from auto-whitelisted by SQLgrey-1.7.4 Received: from mx1.ipf.is (mack.ipf.is [85.197.192.164]) by postgresql.org (Postfix) with ESMTP id DE81A9FB57E for ; Wed, 6 Jun 2007 05:34:17 -0300 (ADT) Received: (qmail 19982 invoked by uid 1010); 6 Jun 2007 08:34:15 +0000 Received: from 88.149.106.19 by mack (envelope-from , uid 1008) with qmail-scanner-1.25-st-qms (clamdscan: 0.88.4/1639. spamassassin: 3.1.4. perlscan: 1.25-st-qms. Clear:RC:1(88.149.106.19):SA:0(-2.4/4.5):. Processed in 2.255515 secs); 06 Jun 2007 08:34:15 -0000 X-Antivirus-HIVE-Mail-From: gnari@hive.is via mack X-Antivirus-HIVE: 1.25-st-qms (Clear:RC:1(88.149.106.19):SA:0(-2.4/4.5):. Processed in 2.255515 secs Process 19957) Received: from dsl-149-106-19.hive.is (HELO ?192.168.1.33?) (88.149.106.19) by mx1.ipf.is with SMTP; 6 Jun 2007 08:34:13 +0000 Subject: Re: How to find missing values across multiple OUTER JOINs From: Ragnar To: Drew Cc: pgsql-sql@postgresql.org In-Reply-To: <4FD9368D-D4CA-44CF-887B-EBB64DCE46BA@fastmail.fm> References: <4FD9368D-D4CA-44CF-887B-EBB64DCE46BA@fastmail.fm> Content-Type: text/plain; charset=ISO-8859-1 Date: Wed, 06 Jun 2007 08:45:46 +0000 Message-Id: <1181119547.5953.31.camel@localhost.localdomain> Mime-Version: 1.0 X-Mailer: Evolution 2.8.1 Content-Transfer-Encoding: 8bit X-Virus-Scanned: Maia Mailguard 1.0.1 X-Archive-Number: 200706/50 X-Sequence-Number: 28540 On ūri, 2007-06-05 at 23:55 -0700, Drew wrote: > I'm having troubles using multiple OUTER JOINs, which I think I want > to use to solve my problem. > > My problem is to find all non-translated string values in our > translations database, given the 4 following tables: > > SOURCE (source_id PRIMARY KEY, language_id, value, ...) > TRANSLATION (translation_id PRIMARY KEY, language_id, value, ...) > TRANSLATION_PAIR (source_id, translation_id) > LANGUAGE(language_id PRIMARY KEY, name) > > This seems to me the appropriate situation for using OUTER JOINs, but > I cannot figure out how to get the null rows without the not-null rows. > > Here's my best guess at this query: > SELECT > s.source_id,tp.translation_pair_id,t.translation_id,t.language_id, > l.name > > FROM source s > LEFT OUTER JOIN translation_pair tp USING(source_id) > LEFT OUTER JOIN translation t ON tp.translation_id = t.translation_id > AND t.translation_id is null move this condition out of the ON clause into a WHERE clause > ) > RIGHT OUTER JOIN language l on l.language_id = t.language_id; SELECT s.source_id, tp.translation_pair_id, t.translation_id, t.language_id, l.name FROM source s LEFT OUTER JOIN translation_pair tp USING(source_id) LEFT OUTER JOIN translation t ON tp.translation_id = t.translation_id RIGHT OUTER JOIN language l on l.language_id =t.language_id WHERE t.translation_id is null; (i did not check the rest of your query) hope this helps, gnari