如何从一个表中选择满足另一个表中所有要求的数据

时间:2014-04-03 04:38:18

标签: oracle

我在这里有一个非常简单的表格,包括申请人,技能和另一张只有技能的表格。我的目标是查看哪些申请人符合所需技能表中的所有要求。

p1爪哇 p1 Oracle
p2爪哇 p2 C#
p2 Oracle
p3 C#

爪哇
C#

SELECT a.NAME
FROM APPLICANTS a, SKILLS s
WHERE a.SKILL = s.SKILL

除了曾经拥有Oracle之外,所有人都回报了我。我曾尝试过GROUP BY HAVING以及过去几个小时内这本书/互联网的变化。我想在这个例子中报告的是p2。这是我手持数据库的第一天,但​​是这个任务的想法似乎很简单但我无法理解。任何帮助,提示或线索都将非常感激。

3 个答案:

答案 0 :(得分:0)

您需要按人分组技能,但将结果限制在技能表中具备技能的人/技能组合

SELECT
    A.NAME, 
FROM
    APPLICANTS A
    INNER JOIN SKILLS ON S.SKILL = A.SKILL
GROUP BY
    A.NAME 
HAVING
    COUNT(*) = (SELECT COUNT(*) FROM SKILLS)

拥有所有技能的人将掌握技能数量=技能表中的技能数量。

假设表中只有一个Person / skill组合,如果你有多行,你应该能够使用子查询来获得Distinct行。

SELECT
    A.Name
FROM
    (SELECT DISTINCT NAME, SKILL FROM APPLICANTS) A
    INNER JOIN SKILLS ON S.SKILL = A.SKILL
GROUP BY
    A.SKILL 
HAVING
    COUNT(*) = (SELECT COUNT(*) FROM SKILLS)

答案 1 :(得分:0)

一种方法是使用标量子查询,在技能表中为申请人的每项技能找到语言,然后从结果中计算非空值

WITH APPLICANTS(P_ID, LANG) AS (
  SELECT 'p1', 'Java' FROM DUAL UNION ALL
  select 'p1', 'Oracle' from dual union all
  SELECT 'P2', 'Java' FROM DUAL UNION ALL
  SELECT 'P2', 'C#' FROM DUAL UNION ALL
  SELECT 'p3', 'Oracle' FROM DUAL UNION ALL
  SELECT 'p3', 'C#' FROM DUAL),
SKILLS (LANG) AS (
  SELECT 'Java' FROM DUAL UNION ALL
  SELECT 'C#'   FROM DUAL),
--------------
--End if data preparation
--------------
APPLICANTS_GROUP AS (SELECT P.P_ID, (SELECT S.LANG FROM SKILLS S WHERE S.LANG = P.LANG AND ROWNUM = 1) LANG
                       FROM APPLICANTS P)
SELECT p_id
  FROM APPLICANTS_GROUP
 WHERE LANG IS NOT NULL
 GROUP BY P_ID
 HAVING COUNT(DISTINCT LANG) = (SELECT COUNT(DISTINCT LANG) FROM SKILLS);

输出:

| P_ID |
|------|
|   P2 |

因此,查询您的表(APPLICANTS和SKILLS)将是

WITH APPLICANTS_GROUP AS (SELECT P.P_ID, (SELECT S.LANG FROM SKILLS S WHERE S.LANG = P.LANG AND ROWNUM = 1) LANG
                            FROM APPLICANTS P)
SELECT p_id
  FROM APPLICANTS_GROUP
 WHERE LANG IS NOT NULL
 GROUP BY P_ID
 HAVING COUNT(DISTINCT LANG) = (SELECT COUNT(DISTINCT LANG) FROM SKILLS);

答案 2 :(得分:0)

谢谢Preet Sangha,你把我放在了正确的轨道上。我不知道你可以查询FROM语句。看起来你回去编辑到我要指出的内容。以前那些没有技能加入的声明返回p1。看起来因为p1有2个技能而且只有2个必需的技能,但它没有检查它们是否是正确的技能。这就是我在编辑之前所遇到的。

SELECT
    A.Name
FROM
   (SELECT APPLICANTS.Name, APPLICANTS.SKILL 
    FROM APPLICANTS, SKILLS
    WHERE APPLICANTS.SKILL = SKILLS.SKILL) A
GROUP BY
    A.Name
HAVING
    COUNT(*) = (SELECT COUNT(*) FROM SKILLS)