简体   繁体   English

如何在嵌套的 SQL SELECT 查询中链接两个值?

[英]How do I link two values in a nested SQL SELECT query?

I have an SQL Server table JobFiles with columns JobId and FileId.我有一个 SQL 服务器表 JobFiles,其中包含 JobId 和 FileId 列。 This table maps which file belongs to which job.该表映射了哪个文件属于哪个作业。 Each job can "contain" one or more files and each file can be "contained" in one or more job.每个作业可以“包含”一个或多个文件,并且每个文件可以“包含”在一个或多个作业中。 For every pair such that job M contains file N there's a row (M,N) in the table.对于作业 M 包含文件 N 的每一对,表中有一行 (M,N)。

I start with a job id and I need to get a list of all files such that they belong to that job only.我从一个作业 ID 开始,我需要获取所有文件的列表,以便它们仅属于该作业。 I have hard time writing a request for that.我很难为此写一个请求。 So far I've crafted the following (pseudocode):到目前为止,我已经制作了以下(伪代码):

SELECT FileId FROM JobFiles WHERE JobId=JobIdICareAbout AND NOT EXISTS
    (SELECT * FROM JobFiles WHERE FileId=ThatSameFileId AND JobId<>JobIdICareAbout);

The above I believe would work but I have a problem of how to map ThatSameFileId onto the FileId returned from the outer SELECT so that the database knows that those are the same.以上我相信会起作用,但我有一个问题,即如何将 map ThatSameFileId到从外部SELECT返回的FileId上,以便数据库知道这些是相同的。

How do I do that?我怎么做? How do I tell the database that FileId in the outer SELECT must be equal to the FileId in the inner SELECT ?如何告诉数据库外部SELECT中的FileId必须等于内部SELECT中的FileId

How about using NOT IN :使用NOT IN怎么样:

SELECT FileId FROM JobFiles WHERE JobId=JobIdICareAbout AND FileID NOT IN
    (SELECT FileId FROM JobFiles WHERE JobId<>JobIdICareAbout);

And a slight variation on that:对此略有不同:

SELECT FileId FROM JobFiles WHERE JobId=JobIdICareAbout
EXCEPT
SELECT FileId FROM JobFiles WHERE JobId<>JobIdICareAbout

I'm taking another approach here but if I understood your problem correctly, it would generate the result you need.我在这里采用了另一种方法,但如果我正确理解了您的问题,它将产生您需要的结果。

Gist of it goes like this它的要点是这样的

  • Get all FileId's from the JobId you care about从你关心的JobId中获取所有FileId's
  • JOIN back with the JobFiles tabel JOIN JobFiles
  • Retain only those FileId's that have no other JobId using a HAVING clause.使用HAVING子句仅保留那些没有其他JobIdFileId's

SQL Statement SQL 声明

SELECT  jf1.FileId
FROM    JobFiles jf1
        INNER JOIN (
          SELECT FileId
          FROM   JobFiles
          WHERE  JobID = JobIdICareAbout
        ) jf2 ON jf2.FileID = jf1.FileID
GROUP BY
        jf1.FileId
HAVING COUNT(*) = 1

Another approach:另一种方法:
LEFT JOIN will only find rows if this file is linked to another job, checking for IS NULL removes those files: LEFT JOIN只会在此文件链接到另一个作业时查找行,检查IS NULL会删除这些文件:

SELECT JobFiles.FileId
FROM JobFiles
LEFT JOIN JobFiles OtherJobFiles ON (     OtherJobFiles.FileId = JobFiles.FileId
                                      AND OtherJobFiles.JobId <> JobIdICareAbout )
WHERE JobFiles.JobId=JobIdICareAbout
  AND OtherJobFiles.FileId IS NULL

It seems you have a lot of (different but) working answers/queries.似乎您有很多(不同但)有效的答案/查询。 Here's one more using NOT EXISTS .这是另一个使用NOT EXISTS的方法。 It's only a correction of what you tried:这只是对您尝试的更正:

SELECT jf.FileId
FROM JobFiles jf 
WHERE jf.JobId = JobIdICareAbout
  AND NOT EXISTS
    ( SELECT 1
      FROM JobFiles jf2
      WHERE jf2.FileId = jf.FileId 
        AND jf2.JobId <> JobIdICareAbout
    )

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

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