如何做一个MYSQL条件选择语句

时间:2013-03-13 01:19:03

标签: mysql sql

背景

我遇到了以下问题,涉及三个表

class_sectors表包含三类类

classes表包含学生可以参加的课程列表

class_choices包含每个部门的学生的第一,第二和第三课程选择。因此对于扇区1,Student_A将class_1作为第一选择,class_3作为第二选择,class_10作为第三选择,然后对于扇区2,他有另外三个选择,等等......

class_choices表包含以下列:

kp_choice_id | kf_personID | kf_sectorID | kf_classID | preference | assigned

我认为列名是不言自明的。 preference是1,2或3.一旦我们审核了学生的选择并将其分配到班级,assigned就是布尔值设置为1。

问题

编写一个sql查询,告诉学生他们为每个扇区分配了哪个类。如果尚未分配他们的课程,则应默认显示他们的第一个偏好。

我实际上有这个工作,但使用两个(非常臃肿?)sql查询如下:

$choices = $db -> Q("SELECT
    *, concat_ws(':', `kf_personID`, `kf_sectorID`) AS `concatids`
FROM
    `class_choices`
WHERE
    (`assigned` = '1')
GROUP BY
    `concatids`
ORDER BY
    `kf_personIDID` ASC,
    `kf_sectorID` ASC;");

$choices2 = $db -> Q("SELECT
    *, concat_ws(':', `kf_personID`, `kf_sectorID`) AS `concatids`
FROM
    `class_choices`
WHERE
    `preference` = '1'
GROUP BY
    `concatids`
HAVING
    `concatids` NOT IN (".iimplode($choices).")
ORDER BY
    `kf_personID` ASC,
    `kf_sectorID` ASC;");

if(is_array($choices2)){
    $choices = array_merge($choices,$choices2);
}

现在$choices确实有我想要的东西。

但我确信有一种方法可以简化这一点,合并两个SQL查询,因此它更轻量级。

是否有某种条件SQL查询可以执行此操作???

1 个答案:

答案 0 :(得分:1)

您的解决方案使用两个步骤来根据需要过滤数据。由于您正在生成报告,这是一个非常好的方法,即使它看起来比您想要的更冗长。

这种方法的优点是调试和维护更容易,这是一个很大的优势。

要改善这种情况,您需要考虑数据结构本身。当我查看class_choices表时,会看到以下字段:kf_classID, preference, assigned,其中包含关键信息。

对于每个班级,assigned字段为0(默认)或1(当为学生分配班级偏好时)。默认情况下,preference = 1的课程是指定的课程,因为您在assigned=0的报告中将其显示在特定部门中所有学生的课程选择中。

可以通过强制执行以下业务规则来改进数据模型:
对于preference=1,请设置默认值assigned=1。当班级选择过程 发生,如果学生被分配了第二或第三选择,则首选项1未分配,并指定备用选项。

这意味着应用程序中的代码更多一些,但它使报告更容易。

难点的来源是分配过程没有明确指定第一个偏好。如果学生无法获得第一选择,它只会更新assigned

总之,您的SQL很好,而改进来自于再次查看数据模型。

希望这会有所帮助,祝你工作顺利!