2017-06-08 2 views
-1

Ich wundere mich, warum ein bedingter Kreuz Join die Bedingung (en) in der WHERE-Klausel angegeben haben muss, und warum es in der ON-Klausel nicht funktioniert. Siehe Link für kompilierte Beispiel: http://rextester.com/IKY8693Warum funktionieren CROSS JOIN-Bedingungen nicht in der ON-Klausel, nur in der WHERE-Klausel?

Business-Kontext: Ich brauche eine Liste von Daten zwischen einem Anfangs- und Enddatum, um in Lücken, um gegen eine dritte Tabelle beitreten zu füllen zu erzeugen, so dass Nullen/Nullen werden für einen bestimmten Monat zurückgegeben.

Wie ich das gemacht habe: Nehmen wir zum Beispiel eine Tabelle von Benutzern, mit JJJJMM Anfangs- und Enddatum.

| user_id | start_yearmonth | end_yearmonth | 
|---------|-----------------|---------------| 
| u9876 | 201504   | 201610  | 
| u5564 | 201602   | 201612  | 
| u4435 | 201606   | NULL   | 

Die zu kreuzende Tabelle ist eine Tabelle der gewünschten YYYYMM-Daten.

| yearmonth | 
|-----------| 
| 201601 | 
| 201602 | 
| 201603 | 
| 201604 | 
| 201605 | 
| 201606 | 
| 201607 | 
| 201608 | 
| 201609 | 
| 201610 | 
| 201611 | 
| 201612 | 
| 201701 | 
| 201702 | 

A CROSS mit Bedingungen in der JOIN where-Klausel funktioniert, aber das funktioniert nicht, wenn die Bedingungen in der ‚ON‘ -Klausel sind. Warum das?

SELECT 
    * 
FROM 
    user_tbl 
    CROSS JOIN date_range 
WHERE 
    user_tbl.start_yearmonth <= date_range.yearmonth 
    AND (user_tbl.end_yearmonth >= date_range.yearmonth 
     OR user_tbl.end_yearmonth IS NULL) 
ORDER BY 
    user_tbl.user_id, date_range.yearmonth ; 
+6

Was meinst du? Cross-Join unterstützt nicht 'on'. Man kann es sich als ein kartesisches Produkt zweier Sets vorstellen, "On" macht keinen Sinn. – freakish

+1

Ich denke meine Frage ist klar - ich frage speziell ** WARUM ** cross join unterstützt nicht 'ON'. 'ON' wird verwendet, um Bedingungen zwischen zwei Tabellen zu erstellen, nicht wahr? – psrpsrpsr

+3

Ja, und Sie erstellen keine Bedingung mit Cross-Join. Andere Arten von Joins haben "On" Bedingung ** obligatorisch **. So einfach ist das. Wenn Sie eine Bedingung zum Cross-Join hinzufügen möchten, müssen Sie dies außerhalb der Cross-Join-Anweisung tun. – freakish

Antwort

2

CROSS JOIN ist der SQL-Operator zum Ausführen eines vollständigen kartesischen Produkts zwischen zwei Tabellen. Da es ein kartesisches Produkt ist, erlaubt es keine Bedingung während der Operation, Sie können sein Ergebnis nur mit einigen Filteroperationen einschränken (die WHERE-Bedingung).

JOIN (INNER und OUTER JOIN, dh) Operatoren, sind einfach kartesisches Produkt zusammen mit dem Filter Operator im ON Teil des Operators (und tatsächlich in der ursprünglichen Syntax von SQL gab es keinen JOIN Operator, einfach die "Komma" -Notation, um das Produkt mit der Join-Bedingung zu bezeichnen, die immer im WHERE-Teil ausgedrückt wird).

Beispiele:

"alte" Notation:

SELECT ... 
FROM table1 t1, table2 t2 
WHERE t1.attribute = t2.attribute 

entspricht die "moderne" Notation:

SELECT ... 
FROM table1 t1 INNER JOIN table2 t2 ON t1.attribute = t2.attribute 

während für das kartesische Produkt:

„alt "Notation:

SELECT ... 
FROM table1 t1, table2 t2 

entsprechen die "moderne" Notation:

SELECT ... 
FROM table1 t1 CROSS JOIN table2 t2 

Mit anderen Worten: JOIN ein CROSS verlangen, dass eine Bedingung tatsächlich eine Art von INNER JOIN ist.

+0

Ausgezeichnete Antwort ohne Luft darüber, danke! – psrpsrpsr

+0

In Standard-SQL * müssen * Sie ein ON mit (INNER) JOIN verwenden. – philipxy

Verwandte Themen