我认为我对桌面连接有很好的把握但是这里有一个我无法弄清楚的问题。
我正在努力跟踪学生在特定课程上取得的进展。在进一步资格认证之前,有些学生需要填写完整的课程清单。
表格(简化):
students
--------
id INT PRIMARY KEY
name VARCHAR(50)
student_courses
---------------
student_id INT PRIMARY KEY
course_id TINYINT PRIMARY KEY
course_status TINYINT (Not done, Started, Completed)
steps_done TINYINT
total_steps TINYINT
date_created DATETIME
date_modified DATETIME
courses
-------
id TINYINT PRIMARY KEY
name VARCHAR(50)
我想在courses
表格中插入必修课程列表,例如5个不同的课程,然后选择一个特定的学生并获取所需课程的列表,是否存在一行当然是在student_courses
表中。
我想我可以在courses
表格中为每个学生插入student_courses
表格中的所有行,但我不希望这样,因为并非所有学生都需要这些课程。如果以后再添加新课程该怎么办呢?
我只想要一个类似这样的结果:
students table:
id name
--- ------------------
1 George Smith
2 Dana Jones
3 Maria Cobblestone
SELECT * FROM students (JOIN bla bla bla - this is the point where I'm lost...)
WHERE students.id = 1
Result:
id name course_id courses.name course_status steps_done
--- ------------------ --------- ------------ ------------- ----------
1 George Smith 1 Botany Not started 0
1 George Smith 2 Biology NULL NULL
1 George Smith 3 Physics NULL NULL
1 George Smith 4 Algebra Completed 34
1 George Smith 5 Sewing Started 2
如果course_status
或steps_done
为NULL
,则表示此学生在student_courses
表中没有针对此课程的行。
然后在MS Access(或其他系统)中使用此功能,并在student_courses
字段中输入值后自动将行插入NULL
表。
答案 0 :(得分:1)
您不能只使用外部联接来执行此操作,您需要先创建一个您感兴趣的所有学生/班级组合的列表,然后在{{1}中使用该列表}。可以使用LEFT JOIN
:
CROSS JOIN
如果需要在Access中完成,也可以使用子查询(在Access中语法不是100%):
;WITH cte AS (SELECT DISTINCT s.id Student_ID
,s.name
,c.id Course_ID
,c.name Class_Name
FROM Students s
CROSS JOIN Courses c)
SELECT cte.*,sc.status
FROM cte
LEFT JOIN student_courses sc
ON cte.course_id = sc.course_id
演示:SQL Fiddle
答案 1 :(得分:1)
你想要一个左外连接。第一个表来自courses
表,用于所需的课程(在where
子句中定义)。
select s.id, s.name, c.id, c.name, c.course_status, c.steps_done
from (courses as c left join
student_courses as sc
on sc.course_id = c.id and
sc.student_id = 1
) left join
students as s
on sc.student_id = s.id
where c.id in (<list of required courses>)
order by s.id, c.id;
我想我已经拥有了所有&#34; Access&#34; isms。
实际上,当他/她错过课程时,上述内容将缺少学生姓名。以下更正确:
select s.id, s.name, c.id, c.name, c.course_status, c.steps_done
from (courses as c left join
student_courses as sc
on sc.course_id = c.id and
sc.student_id = 1
) cross join
students as s
on s.id = 1
where c.id in (<list of required courses>)
order by s.id, c.id;