简体   繁体   English

PHP / SQL:如何从一个表中选择完全不同的表中不存在的值

[英]PHP/SQL: How to SELECT values from one table that do not exist in a completely different table

I have two tables, one with a list of projects and who is assigned to each project, and one with names and information about contractors. 我有两个表,一个表包含项目列表,每个项目分配给谁,另一个表包含承包商的名称和信息。

"Projects_table"
Project_ID    Contractor_assigned    Job_Complete
1             Jim Smith              1
2             John Smith             0
3             Edward Smith           0
4             Smith Smith            1
5             Candle Stick           1

and

"Contractors_Table"
Contractor_ID    Name              Drywall     Insulation
1                Jim Smith         1           0
2                John Smith        0           1
3                Edward Smith      0           1
4                Smith Smith       0           1
5                Jack BeNimble     0           1
6                Jack BeQuick      1           0
7                Candle Stick      0           1

What I need, is to pull an SQL query that gives me a list of the Contractors of a certain type (Drywall or Insulator) who are currently not assigned to any job, so long as that job is also not marked "Complete." 我需要的是,拉出一个SQL查询,该查询会向我提供当前未分配给任何作业的某种类型的承包商(干墙或绝缘子)的列表,只要该作业也未标记为“已完成”即可。

I've tried a few versions of this, but with no success: 我已经尝试了几个版本,但是没有成功:

SELECT
Name FROM Contractors_Table
WHERE Contractors_Table.Insulation=1
AND Name NOT IN
(SELECT Contractor_assigned FROM Projects_table WHERE `Job_Complete` = 0)

What I'm hoping for output from my above example is to get back: 我希望从以上示例中获得的输出是:

Jack BeNimble
Candle Stick

Those two Insulators are not currently assigned a job, excluding the "complete" job. 这两个绝缘子当前未分配工作,“完成”工作除外。

You should use NOT EXISTS instead: 您应该改用NOT EXISTS

SELECT Name
  FROM Contractors_Table c
 WHERE c.Insulation = 1
   AND NOT EXISTS
       (SELECT 1 
          FROM Projects_table p
         WHERE p.Job_Complete = 0
           AND p.Contractor_assigned = c.Name)

You could refactor the query you are trying to do, but will take much more effort to use NOT IN . 您可以重构您要执行的查询,但是使用NOT IN会花费更多的精力。

You should also use foreign keys instead of names to compare data. 您还应该使用foreign keys而不是名称来比较数据。 You are duplicating information in relational database, which doesn't follow Normalization rules 您正在关系数据库中复制信息,该数据库不遵循规范化规则

Firstly your table design is wrong: you should store the Contractor_ID in the project table, and not their names (what happens with homonyms???) 首先,您的表设计是错误的:您应该将Contractor_ID存储在项目表中,而不是它们的名称(同音字会​​发生什么???)

Secondly I don't understand why your query doesnt return the expected result because it looks correct. 其次,我不明白您的查询为什么不返回预期结果,因为它看起来正确。 Maybe because you have a column named Name , and this is a reserved keyword, and you should thus surround it with ` 可能是因为您有一个名为Name的列,并且这是一个保留关键字,因此应在其周围加上`

Anyway it's never efficient to do a NOT IN 不管怎样,做一个NOT IN从来都没有效率

You can rewrite that with an OUTER JOIN : 您可以使用OUTER JOIN重写它:

SELECT C.`Name` 
FROM Contractors_Table C
LEFT JOIN Projects_table P ON C.`Name` = P.`Contractor_assigned` AND P.`Job_Complete` = 0
WHERE C.Insulation=1
  AND P.ID IS NULL --> This will ensure that you only get those who are not in the Project table

Obviously a couple of queries (one for each type). 显然有几个查询(每种类型一个)。 If you use unique ID's in both tables for each of the contractors you can join the tables and select where Contractors_Table.drywall = 0 and Project_Table = 0 (Group by Contractor ID). 如果您在两个表中为每个承包商使用唯一的ID,则可以联接这些表,然后选择Contractors_Table.drywall = 0和Project_Table = 0(按承包商ID分组)。

I think its just about getting your data sorted in your tables then writing the query. 我认为这只是要让您的数据在表中排序然后编写查询。

HTH :-) HTH :-)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM