Oracle PL/SQL Tutorial/Query Select/EXISTS

Материал из SQL эксперт
Перейти к: навигация, поиск

EXISTS and NOT EXISTS Versus IN and NOT IN

  1. EXISTS is different from IN.
  2. EXISTS just checks for the existence of rows, whereas IN checks actual values.
  3. EXISTS typically offers better performance than IN with subqueries.
  4. You should use EXISTS rather than IN wherever possible.
  5. When a list of values contains a null, NOT EXISTS returns true, but NOT IN returns false.



SQL> -- create demo table
SQL> create table Employee(
  2    EMPNO         NUMBER(3),
  3    ENAME         VARCHAR2(15 BYTE),
  4    HIREDATE      DATE,
  5    ORIG_SALARY   NUMBER(6),
  6    CURR_SALARY   NUMBER(6),
  7    REGION        VARCHAR2(1 BYTE),
  8    MANAGER_ID    NUMBER(3)
  9  )
 10  /
Table created.
SQL>
SQL> create table job (
  2    EMPNO         NUMBER(3),
  3    jobtitle      VARCHAR2(20 BYTE)
  4  )
  5  /
Table created.
SQL>
SQL> insert into job (EMPNO, Jobtitle) values (1,"Tester");
1 row created.
SQL> insert into job (EMPNO, Jobtitle) values (2,"Accountant");
1 row created.
SQL> insert into job (EMPNO, Jobtitle) values (3,"Developer");
1 row created.
SQL> insert into job (EMPNO, Jobtitle) values (4,"COder");
1 row created.
SQL> insert into job (EMPNO, Jobtitle) values (5,"Director");
1 row created.
SQL> insert into job (EMPNO, Jobtitle) values (6,"Mediator");
1 row created.
SQL> insert into job (EMPNO, Jobtitle) values (7,"Proffessor");
1 row created.
SQL> insert into job (EMPNO, Jobtitle) values (8,"Programmer");
1 row created.
SQL> insert into job (EMPNO, Jobtitle) values (9,"Developer");
1 row created.
SQL>
SQL>
SQL> -- prepare data
SQL> insert into Employee(EMPNO,  EName,   HIREDATE,                       ORIG_SALARY,       CURR_SALARY,  REGION, MANAGER_ID)
  2               values (1,      "Jason", to_date("19960725","YYYYMMDD"), 1234,              8767,         "E",    2)
  3  /
1 row created.
SQL> insert into Employee(EMPNO,  EName,   HIREDATE,                       ORIG_SALARY,       CURR_SALARY,  REGION, MANAGER_ID)
  2               values (2,      "John",  to_date("19970715","YYYYMMDD"), 2341,              3456,         "W",    3)
  3  /
1 row created.
SQL> insert into Employee(EMPNO,  EName,   HIREDATE,                       ORIG_SALARY,       CURR_SALARY,  REGION, MANAGER_ID)
  2               values (3,      "Joe",   to_date("19860125","YYYYMMDD"), 4321,              5654,         "E",    3)
  3  /
1 row created.
SQL> insert into Employee(EMPNO,  EName,   HIREDATE,                       ORIG_SALARY,       CURR_SALARY,  REGION, MANAGER_ID)
  2               values (4,      "Tom",   to_date("20060913","YYYYMMDD"), 2413,              6787,         "W",    4)
  3  /
1 row created.
SQL> insert into Employee(EMPNO,  EName,   HIREDATE,                       ORIG_SALARY,       CURR_SALARY,  REGION, MANAGER_ID)
  2               values (5,      "Jane",  to_date("20050417","YYYYMMDD"), 7654,              4345,         "E",    4)
  3  /
1 row created.
SQL> insert into Employee(EMPNO,  EName,   HIREDATE,                       ORIG_SALARY,       CURR_SALARY,  REGION, MANAGER_ID)
  2               values (6,      "James", to_date("20040718","YYYYMMDD"), 5679,              6546,         "W",    5)
  3  /
1 row created.
SQL> insert into Employee(EMPNO,  EName,   HIREDATE,                       ORIG_SALARY,       CURR_SALARY,  REGION, MANAGER_ID)
  2               values (7,      "Jodd",  to_date("20030720","YYYYMMDD"), 5438,              7658,         "E",    6)
  3  /
1 row created.
SQL> insert into Employee(EMPNO,  EName,   HIREDATE,                       ORIG_SALARY,       CURR_SALARY,  REGION)
  2               values (8,      "Joke",  to_date("20020101","YYYYMMDD"), 8765,              4543,         "W")
  3  /
1 row created.
SQL> insert into Employee(EMPNO,  EName,   HIREDATE,                       ORIG_SALARY,       CURR_SALARY,  REGION)
  2               values (9,      "Jack",  to_date("20010829","YYYYMMDD"), 7896,              1232,         "E")
  3  /
1 row created.
SQL>
SQL>
SQL>
SQL> -- display data in the table
SQL> select * from Employee
  2  /
     EMPNO ENAME           HIREDATE  ORIG_SALARY CURR_SALARY R MANAGER_ID
---------- --------------- --------- ----------- ----------- - ----------
         1 Jason           25-JUL-96        1234        8767 E          2
         2 John            15-JUL-97        2341        3456 W          3
         3 Joe             25-JAN-86        4321        5654 E          3
         4 Tom             13-SEP-06        2413        6787 W          4
         5 Jane            17-APR-05        7654        4345 E          4
         6 James           18-JUL-04        5679        6546 W          5
         7 Jodd            20-JUL-03        5438        7658 E          6
         8 Joke            01-JAN-02        8765        4543 W
         9 Jack            29-AUG-01        7896        1232 E
9 rows selected.
SQL> select * from job
  2  /
     EMPNO JOBTITLE
---------- --------------------
         1 Tester
         2 Accountant
         3 Developer
         4 COder
         5 Director
         6 Mediator
         7 Proffessor
         8 Programmer
         9 Developer
9 rows selected.
SQL>
SQL> SELECT empno, ename
  2  FROM employee
  3  WHERE NOT EXISTS (null);
WHERE NOT EXISTS (null)
                  *
ERROR at line 3:
ORA-00928: missing SELECT keyword

SQL>
SQL>
SQL> -- clean the table
SQL> drop table Employee
  2  /
Table dropped.
SQL> drop table job
  2  /
Table dropped.


exists in subquery

SQL>
SQL> create table emp
  2  ( empno      NUMBER(4)    constraint E_PK primary key
  3  , ename      VARCHAR2(8)
  4  , init       VARCHAR2(5)
  5  , job        VARCHAR2(8)
  6  , mgr        NUMBER(4)
  7  , bdate      DATE
  8  , sal        NUMBER(6,2)
  9  , comm       NUMBER(6,2)
 10  , deptno     NUMBER(2)    default 10
 11  ) ;
Table created.
SQL> insert into emp values(1,"Tom","N",   "TRAINER", 13,date "1965-12-17",  800 , NULL,  20);
1 row created.
SQL> insert into emp values(2,"Jack","JAM", "Tester",6,date "1961-02-20",  1600, 300,   30);
1 row created.
SQL> insert into emp values(3,"Wil","TF" ,  "Tester",6,date "1962-02-22",  1250, 500,   30);
1 row created.
SQL> insert into emp values(4,"Jane","JM",  "Designer", 9,date "1967-04-02",  2975, NULL,  20);
1 row created.
SQL> insert into emp values(5,"Mary","P",  "Tester",6,date "1956-09-28",  1250, 1400,  30);
1 row created.
SQL> insert into emp values(6,"Black","R",   "Designer", 9,date "1963-11-01",  2850, NULL,  30);
1 row created.
SQL> insert into emp values(7,"Chris","AB",  "Designer", 9,date "1965-06-09",  2450, NULL,  10);
1 row created.
SQL> insert into emp values(8,"Smart","SCJ", "TRAINER", 4,date "1959-11-26",  3000, NULL,  20);
1 row created.
SQL> insert into emp values(9,"Peter","CC",   "Designer",NULL,date "1952-11-17",  5000, NULL,  10);
1 row created.
SQL> insert into emp values(10,"Take","JJ", "Tester",6,date "1968-09-28",  1500, 0,     30);
1 row created.
SQL> insert into emp values(11,"Ana","AA",  "TRAINER", 8,date "1966-12-30",  1100, NULL,  20);
1 row created.
SQL> insert into emp values(12,"Jane","R",   "Manager",   6,date "1969-12-03",  800 , NULL,  30);
1 row created.
SQL> insert into emp values(13,"Fake","MG",   "TRAINER", 4,date "1959-02-13",  3000, NULL,  20);
1 row created.
SQL> insert into emp values(14,"Mike","TJA","Manager",   7,date "1962-01-23",  1300, NULL,  10);
1 row created.
SQL> create table offerings
  2  ( course     VARCHAR2(6)
  3  , begindate  DATE
  4  , trainer    NUMBER(4)
  5  , location   VARCHAR2(8)
  6  ) ;
Table created.
SQL> insert into offerings values ("SQL",date "2009-04-12",13,"DALLAS" );
1 row created.
SQL> insert into offerings values ("OAU",date "2009-08-10",4,"CHICAGO");
1 row created.
SQL> insert into offerings values ("SQL",date "2009-10-04",1,"SEATTLE");
1 row created.
SQL> insert into offerings values ("SQL",date "2009-12-13",1,"DALLAS" );
1 row created.
SQL> insert into offerings values ("JAV",date "2009-12-13",4,"SEATTLE");
1 row created.
SQL> insert into offerings values ("XML",date "2000-02-03",1,"DALLAS" );
1 row created.
SQL> insert into offerings values ("JAV",date "2000-02-01",11,"DALLAS" );
1 row created.
SQL> insert into offerings values ("PLS",date "2000-09-11",8,"DALLAS" );
1 row created.
SQL> insert into offerings values ("XML",date "2000-09-18",NULL,"SEATTLE");
1 row created.
SQL> insert into offerings values ("OAU",date "2000-09-27",13,"DALLAS" );
1 row created.
SQL> insert into offerings values ("ERM",date "2001-01-15",NULL, NULL    );
1 row created.
SQL> insert into offerings values ("PRO",date "2001-02-19",NULL,"DALLAS" );
1 row created.
SQL> insert into offerings values ("RSD",date "2001-02-24",8,"CHICAGO");
1 row created.
SQL>
SQL> select e.*
  2  from   emp e
  3  where  exists (select o.*
  4                 from   offerings o
  5                 where  o.course = "SQL"
  6                 and    o.trainer = e.empno);
     EMPNO ENAME    INIT  JOB             MGR BDATE             SAL       COMM
---------- -------- ----- -------- ---------- ---------- ---------- ----------
    DEPTNO
----------
         1 Tom      N     TRAINER          13 17-12-1965        800
        20
        13 Fake     MG                      4 13-02-1959       3000
        20

SQL> drop table offerings;
Table dropped.
SQL> drop table emp;
Table dropped.
SQL>


Exist with subquery

SQL>
SQL> create table course_schedule
  2  ( course     VARCHAR2(6)
  3  , begindate  DATE
  4  , trainer    NUMBER(4)
  5  , location   VARCHAR2(20)) ;
Table created.
SQL>
SQL>
SQL> insert into course_schedule values ("SQL",date "1999-04-12",1,"VANCOUVER" );
1 row created.
SQL> insert into course_schedule values ("OAU",date "1999-08-10",2,"CHICAGO");
1 row created.
SQL> insert into course_schedule values ("SQL",date "1999-10-04",3,"SEATTLE");
1 row created.
SQL> insert into course_schedule values ("SQL",date "1999-12-13",4,"DALLAS" );
1 row created.
SQL> insert into course_schedule values ("JAV",date "1999-12-13",5,"SEATTLE");
1 row created.
SQL> insert into course_schedule values ("XML",date "2000-02-03",6,"VANCOUVER" );
1 row created.
SQL> insert into course_schedule values ("JAV",date "2000-02-01",7,"DALLAS" );
1 row created.
SQL> insert into course_schedule values ("PLS",date "2000-09-11",8,"VANCOUVER" );
1 row created.
SQL> insert into course_schedule values ("XML",date "2000-09-18",NULL,"SEATTLE");
1 row created.
SQL> insert into course_schedule values ("OAU",date "2000-09-27",9,"DALLAS" );
1 row created.
SQL> insert into course_schedule values ("ERM",date "2001-01-15",10, NULL    );
1 row created.
SQL> insert into course_schedule values ("PRO",date "2001-02-19",NULL,"VANCOUVER" );
1 row created.
SQL> insert into course_schedule values ("RSD",date "2001-02-24",8,"CHICAGO");
1 row created.
SQL>
SQL> create table employees(
  2    empno      NUMBER(4)
  3  , ename      VARCHAR2(8)
  4  , init       VARCHAR2(5)
  5  , job        VARCHAR2(8)
  6  , mgr        NUMBER(4)
  7  , bdate      DATE
  8  , msal       NUMBER(6,2)
  9  , comm       NUMBER(6,2)
 10  , deptno     NUMBER(2) ) ;
Table created.
SQL>
SQL>
SQL> insert into employees values(1,"Jason",  "N",  "TRAINER", 2,   date "1965-12-18",  800 , NULL,  10);
1 row created.
SQL> insert into employees values(2,"Jerry",  "J",  "SALESREP",3,   date "1966-11-19",  1600, 300,   10);
1 row created.
SQL> insert into employees values(3,"Jord",   "T" , "SALESREP",4,   date "1967-10-21",  1700, 500,   20);
1 row created.
SQL> insert into employees values(4,"Mary",   "J",  "MANAGER", 5,   date "1968-09-22",  1800, NULL,  20);
1 row created.
SQL> insert into employees values(5,"Joe",    "P",  "SALESREP",6,   date "1969-08-23",  1900, 1400,  30);
1 row created.
SQL> insert into employees values(6,"Black",  "R",  "MANAGER", 7,   date "1970-07-24",  2000, NULL,  30);
1 row created.
SQL> insert into employees values(7,"Red",    "A",  "MANAGER", 8,   date "1971-06-25",  2100, NULL,  40);
1 row created.
SQL> insert into employees values(8,"White",  "S",  "TRAINER", 9,   date "1972-05-26",  2200, NULL,  40);
1 row created.
SQL> insert into employees values(9,"Yellow", "C",  "DIRECTOR",10,  date "1973-04-27",  2300, NULL,  20);
1 row created.
SQL> insert into employees values(10,"Pink",  "J",  "SALESREP",null,date "1974-03-28",  2400, 0,     30);
1 row created.
SQL>
SQL>
SQL>
SQL> select e.*
  2  from   employees e
  3  where  exists (select o.*
  4                 from   course_schedule o
  5                 where  o.course = "SQL"
  6                 and    o.trainer = e.empno);
     EMPNO ENAME    INIT  JOB             MGR BDATE           MSAL       COMM     DEPTNO
---------- -------- ----- -------- ---------- --------- ---------- ---------- ----------
         1 Jason    N     TRAINER           2 18-DEC-65        800                    10
         3 Jord     T     SALESREP          4 21-OCT-67       1700        500         20
         4 Mary     J     MANAGER           5 22-SEP-68       1800                    20
SQL>
SQL> drop table employees;
Table dropped.
SQL>
SQL> drop table course_schedule;
Table dropped.
SQL>


not exists and subquery

SQL>
SQL> create table offerings
  2  ( course     VARCHAR2(6)
  3  , begindate  DATE
  4  , trainer    NUMBER(4)
  5  , location   VARCHAR2(8)
  6  ) ;
Table created.
SQL> insert into offerings values ("SQL",date "2009-04-12",13,"DALLAS" );
1 row created.
SQL> insert into offerings values ("OAU",date "2009-08-10",4,"CHICAGO");
1 row created.
SQL> insert into offerings values ("SQL",date "2009-10-04",1,"SEATTLE");
1 row created.
SQL> insert into offerings values ("SQL",date "2009-12-13",1,"DALLAS" );
1 row created.
SQL> insert into offerings values ("JAV",date "2009-12-13",4,"SEATTLE");
1 row created.
SQL> insert into offerings values ("XML",date "2000-02-03",1,"DALLAS" );
1 row created.
SQL> insert into offerings values ("JAV",date "2000-02-01",11,"DALLAS" );
1 row created.
SQL> insert into offerings values ("PLS",date "2000-09-11",8,"DALLAS" );
1 row created.
SQL> insert into offerings values ("XML",date "2000-09-18",NULL,"SEATTLE");
1 row created.
SQL> insert into offerings values ("OAU",date "2000-09-27",13,"DALLAS" );
1 row created.
SQL> insert into offerings values ("ERM",date "2001-01-15",NULL, NULL    );
1 row created.
SQL> insert into offerings values ("PRO",date "2001-02-19",NULL,"DALLAS" );
1 row created.
SQL> insert into offerings values ("RSD",date "2001-02-24",8,"CHICAGO");
1 row created.
SQL> create table registrations
  2  ( attendee    NUMBER(4)
  3  , course      VARCHAR2(6)
  4  , begindate   DATE
  5  , evaluation  NUMBER(1)
  6  , constraint  R_PK        primary key(attendee,course,begindate)
  7  ) ;
Table created.
SQL>
SQL> insert into registrations values (2,"SQL",date "2009-04-12",4   );
1 row created.
SQL> insert into registrations values (14,"SQL",date "2009-04-12",5   );
1 row created.
SQL> insert into registrations values (6,"SQL",date "2009-04-12",4   );
1 row created.
SQL> insert into registrations values (11,"SQL",date "2009-04-12",2   );
1 row created.
SQL> insert into registrations values (8,"SQL",date "2009-10-04",NULL);
1 row created.
SQL> insert into registrations values (9,"SQL",date "2009-10-04",3   );
1 row created.
SQL> insert into registrations values (13,"SQL",date "2009-10-04",4   );
1 row created.
SQL> insert into registrations values (13,"SQL",date "2009-12-13",NULL);
1 row created.
SQL> insert into registrations values (6,"SQL",date "2009-12-13",NULL);
1 row created.
SQL> insert into registrations values (3,"OAU",date "2009-08-10",4   );
1 row created.
SQL>
SQL> select o.*
  2  from   offerings o
  3  where  not exists
  4        (select r.*
  5         from   registrations r
  6         where  r.course    = o.course
  7         and    r.begindate = o.begindate);
COURSE BEGINDATE     TRAINER LOCATION
------ ---------- ---------- --------
JAV    13-12-2009          4 SEATTLE
XML    03-02-2000          1 DALLAS
JAV    01-02-2000         11 DALLAS
PLS    11-09-2000          8 DALLAS
XML    18-09-2000            SEATTLE
OAU    27-09-2000         13 DALLAS
ERM    15-01-2001
PRO    19-02-2001            DALLAS
RSD    24-02-2001          8 CHICAGO
9 rows selected.
SQL> drop table offerings;
Table dropped.
SQL> drop table registrations;
Table dropped.
SQL>


Not Exist with subquery

SQL>
SQL> create table course_schedule
  2  ( course     VARCHAR2(6)
  3  , begindate  DATE
  4  , trainer    NUMBER(4)
  5  , location   VARCHAR2(20)) ;
Table created.
SQL>
SQL>
SQL> insert into course_schedule values ("SQL",date "1999-04-12",1,"VANCOUVER" );
1 row created.
SQL> insert into course_schedule values ("OAU",date "1999-08-10",2,"CHICAGO");
1 row created.
SQL> insert into course_schedule values ("SQL",date "1999-10-04",3,"SEATTLE");
1 row created.
SQL> insert into course_schedule values ("SQL",date "1999-12-13",4,"DALLAS" );
1 row created.
SQL> insert into course_schedule values ("JAV",date "1999-12-13",5,"SEATTLE");
1 row created.
SQL> insert into course_schedule values ("XML",date "2000-02-03",6,"VANCOUVER" );
1 row created.
SQL> insert into course_schedule values ("JAV",date "2000-02-01",7,"DALLAS" );
1 row created.
SQL> insert into course_schedule values ("PLS",date "2000-09-11",8,"VANCOUVER" );
1 row created.
SQL> insert into course_schedule values ("XML",date "2000-09-18",NULL,"SEATTLE");
1 row created.
SQL> insert into course_schedule values ("OAU",date "2000-09-27",9,"DALLAS" );
1 row created.
SQL> insert into course_schedule values ("ERM",date "2001-01-15",10, NULL    );
1 row created.
SQL> insert into course_schedule values ("PRO",date "2001-02-19",NULL,"VANCOUVER" );
1 row created.
SQL> insert into course_schedule values ("RSD",date "2001-02-24",8,"CHICAGO");
1 row created.
SQL>
SQL> create table registrations
  2  ( attendee    NUMBER(4)
  3  , course      VARCHAR2(6)
  4  , begindate   DATE
  5  , evaluation  NUMBER(1)) ;
Table created.
SQL>
SQL>
SQL> insert into registrations values (1, "SQL",date "1999-04-12",4   );
1 row created.
SQL> insert into registrations values (2, "SQL",date "1999-12-13",NULL);
1 row created.
SQL> insert into registrations values (3, "SQL",date "1999-12-13",NULL);
1 row created.
SQL> insert into registrations values (4, "OAU",date "1999-08-10",4   );
1 row created.
SQL> insert into registrations values (5, "OAU",date "2000-09-27",5   );
1 row created.
SQL> insert into registrations values (6, "JAV",date "1999-12-13",2   );
1 row created.
SQL> insert into registrations values (7, "JAV",date "2000-02-01",4   );
1 row created.
SQL> insert into registrations values (8, "JAV",date "2000-02-01",5   );
1 row created.
SQL> insert into registrations values (9, "XML",date "2000-02-03",4   );
1 row created.
SQL> insert into registrations values (10,"XML",date "2000-02-03",5   );
1 row created.
SQL> insert into registrations values (1, "PLS",date "2000-09-11",NULL);
1 row created.
SQL> insert into registrations values (2, "PLS",date "2000-09-11",NULL);
1 row created.
SQL> insert into registrations values (3, "PLS",date "2000-09-11",NULL);
1 row created.
SQL>
SQL>
SQL>
SQL> select o.*
  2  from   course_schedule o
  3  where  not exists
  4        (select r.*
  5         from   registrations r
  6         where  r.course    = o.course
  7         and    r.begindate = o.begindate);
COURSE BEGINDATE    TRAINER LOCATION
------ --------- ---------- --------------------
SQL    04-OCT-99          3 SEATTLE
XML    18-SEP-00            SEATTLE
PRO    19-FEB-01            VANCOUVER
ERM    15-JAN-01         10
RSD    24-FEB-01          8 CHICAGO
SQL>
SQL> drop table course_schedule;
Table dropped.
SQL>
SQL> drop table registrations;
Table dropped.
SQL>
SQL>


Using the EXISTS Operator with subquery

SQL> CREATE TABLE empExam (
  2     empID  INT NOT NULL,
  3     ExamID     INT NOT NULL,
  4     Mark       INT,
  5     Taken   SMALLINT,
  6     Comments   VARCHAR(255),
  7     CONSTRAINT PK_empExam PRIMARY KEY (empID, ExamID));
Table created.
SQL>
SQL>
SQL> INSERT INTO empExam (empID,ExamID,Mark,Taken,Comments) VALUES (1,1,55,1,"Satisfactory");
1 row created.
SQL> INSERT INTO empExam (empID,ExamID,Mark,Taken,Comments) VALUES (1,2,73,1,"Good result");
1 row created.
SQL> INSERT INTO empExam (empID,ExamID,Mark,Taken,Comments) VALUES (2,3,44,1,"Hard");
1 row created.
SQL> INSERT INTO empExam (empID,ExamID,Mark,Taken,Comments) VALUES (2,5,39,0,"Simple");
1 row created.
SQL> INSERT INTO empExam (empID,ExamID,Mark,Taken) VALUES (2,6,63,1);
1 row created.
SQL>
SQL>
SQL>
SQL> CREATE TABLE emp (
  2     empID INT NOT NULL PRIMARY KEY,
  3     Name      VARCHAR(50) NOT NULL);
Table created.
SQL> INSERT INTO emp (empID,Name) VALUES (1,"Tom");
1 row created.
SQL> INSERT INTO emp (empID,Name) VALUES (2,"Jack");
1 row created.
SQL> INSERT INTO emp (empID,Name) VALUES (3,"Mary");
1 row created.
SQL> INSERT INTO emp (empID,Name) VALUES (4,"Bill");
1 row created.
SQL> INSERT INTO emp (empID,Name) VALUES (5,"Cat");
1 row created.
SQL> INSERT INTO emp (empID,Name) VALUES (6,"Victor");
1 row created.
SQL>
SQL>
SQL> SELECT empID, Name FROM emp s
  2  WHERE EXISTS (
  3     SELECT empID FROM empExam e
  4     WHERE Mark < 40 AND e.empID = s.empID);
     EMPID NAME
---------- --------------------------------------------------
         2 Jack
1 row selected.
SQL>
SQL>
SQL>
SQL> drop table emp;
Table dropped.
SQL> drop table empExam;
Table dropped.