Oracle
 sql >> Datenbank >  >> RDS >> Oracle

Wie man die relationale Division (einfacher Algebra-Ausdruck) in Bezug auf SQL darstellt

Angesichts dieser DDL für Tabellen, die Ihren relevanten Beziehungen entsprechen:

create table Boats(
  bid int,
  bname varchar(50),
  color varchar(50)
);

create table Reserves(
  sid int,
  bid int,
  day date
);

Sie können die Divisionsformel (3) ziemlich einfach in die Oracle SQL-Syntax übertragen, obwohl sie ausführlich ist:

-- All sailors who reserved at least one boat
SELECT DISTINCT sid
FROM Reserves

MINUS 

-- All sailors who reserved at least one boat, but not all of them
SELECT sid
FROM (
  -- all combinations of a sailor who reserved any boat with any boat
  -- available to be reserved:
  SELECT Reserves.sid, Boats.bid
  FROM
    Reserves
    CROSS JOIN
    Boats

  MINUS

  -- all combinations of sailor and boat for actual reservations made
  SELECT sid, bid
  FROM Reserves
) sids

Wie angegeben, verwendet das nur den CROSS JOIN und MINUS Operationen, um direkt der Formel der relationalen Algebra zu entsprechen. In einer realen Datenbankanwendung würde man jedoch sicherlich dasselbe Ergebnis über eine völlig andere Abfrage erhalten.

Beachten Sie auch, dass SQL-Datenbanken gegen das Prinzip der formalen relationalen Algebra verstoßen können und dies auch tun, dass Relationen keine doppelten Tupel enthalten. Das ist der Grund für SELECT DISTINCT in der ersten Unterabfrage. Eine eindeutige Auswahl, die strategisch an anderer Stelle in der Abfrage angewendet wird, könnte sie effizienter machen, würde aber das Ergebnis nicht verändern.