create table tblcourse(pid number,course varchar2(20));
Insert into TBLCOURSE  (PID, COURSE) Values (1, 'COURSE1');
Insert into TBLCOURSE  (PID, COURSE) Values (1, 'COURSE3');
Insert into TBLCOURSE  (PID, COURSE) Values (1, 'COURSE5');
Insert into TBLCOURSE  (PID, COURSE) Values (2, 'COURSE8');
Insert into TBLCOURSE  (PID, COURSE) Values (3, 'COURSE8');
Insert into TBLCOURSE  (PID, COURSE) Values (4, 'COURSE2');
Insert into TBLCOURSE  (PID, COURSE) Values (5, 'COURSE4');
Insert into TBLCOURSE  (PID, COURSE) Values (5, 'COURSE6');
COMMIT;
询问 :
WITH TAB AS 
(
 SELECT DISTINCT(COURSE) as course  
   FROM tblcourse --distinct courses  
MINUS   
 SELECT DISTINCT(COURSE) as course  
  FROM tblcourse 
 WHERE pid=:pid --will give you distinct courses that pid subscribe
)
SELECT  :pid,LISTAGG(COURSE, ',') WITHIN GROUP (ORDER BY COURSE) as courses 
  FROM TAB;
结果如你所愿: pass pid as 1
PID           COURSES
-------------------------
 1            COURSE2,COURSE4,COURSE6,COURSE8
SQLFIDDLE 中的试用示例
编辑
我想不出更好的解决方案,可能有人可以提出更好的方法来做到这一点,同时你可以看看这个,但有时笛卡尔积会摇摆不定:) 
WITH course_cartesian as (
       SELECT pid,course 
         FROM (SELECT DISTINCT course 
                 FROM tblcourse)q1,
              (SELECT DISTINCT pid 
                 FROM tblcourse)q2 
             ORDER BY pid,course
   )
,tbl_course AS(SELECT pid,course 
                 FROM course_cartesian
                MINUS
              SELECT pid,course FROM tblcourse
              )
SELECT pid,listagg(course,',') WITHIN GROUP (ORDER BY course) as courses 
  FROM   tbl_course  
 GROUP BY pid 
 ORDER BY pid;
输出

SQLFIDDLE链接