2012-03-17 11 views
0

2つのテーブルがあります。 1つはプロジェクトのリストを含み、もう1つはそれらのプロジェクトのタスクのリストを含む。関連するすべてのレコードが文字列と等しいすべてのレコードを取得します。

すべてのタスクのステータスが「完了」であるプロジェクトのみのリストを取得します。

プロジェクト表:

は私のデータは、このようになります

ID,ProjectName,ProjectStatus 

タスク表:私はすべてのレコードを取得するための基本的なSELECT文を行うことができます

ID, ProjectID, TaskName, TaskStatus 

Tasks.ProjectID = Projects.ID

、そして、TaskStatusが特定の状態である場所をフィルタリングできますが、再び私は、すべてのタスクが完了したプロジェクトのリストがほしいだけです。

ありがとうございました!

select * 
    from Projects 
where ID NOT IN (select ProjectID from Tasks where TaskStatus = 'COMPLETE') 

1または使用するかどうか:あなたはまた、サブクエリではありませんを使用することができます

を完了するために、

select * 
    from Projects P 
where NOT EXISTS (select 1 from Tasks where Tasks.ProjectID = P.ID and TaskStatus <> 'COMPLETE') 

編集:

+1

を:あなたは、関連するすべてのタスクが完了していると言うとき、あなたはそのゼロ以上のタスクのすべてを意味し、従来の方法で用語を使用しているが完了している、またはプロジェクトによって少なくとも1つのタスクが必要になることはありますか?通常、関連するタスクを持たないプロジェクトは、あなたが望むものになりますが、一部の人は、面白く非古典的な方法で「すべて」を使用します。 –

+0

清算についてお尋ねいただきありがとうございます。私はすべてを意味しました。プロジェクトが作成されたときに最初のタスクを作成するようにアプリケーションを作成しました。 –

答えて

1

あなたはサブクエリをEXISTS、NOTを使用することができますそれ以外の場合は、テーブルのデータ量とインデックスに依存します:

最初のオプションは、親クエリの各行に対してサブクエリを実行しますが、ProjectIDインデックスによって(存在する場合はおそらくyes)アクセスします。

2番目のオプションは、最初にサブクエリを実行し、サブクエリ結果を使用して親クエリを実行します。しかし、サブクエリはおそらくインデックスを使用しません。なぜなら、TaskStatusフィールドにインデックスを持たない可能性が高いからです(あまり意味がないでしょう)。

しかし、タスクテーブルに多くの行がない場合は、テーブルのフルスキャンを行うほうが安いため、インデックスは使用されません。だから私の推薦は、実行計画をチェックし、コストを比較し、可能であれば、いくつかのベンチマークを実行して、このオプションまたは他の場合に適したオプションを決定します。

+0

ありがとうございます。これはまさに私が必要としていたものです。 –

+0

cool!答えでそれを選んでください! :) –

0

この試してみてください。念のため今

SELECT ID, ProjectName   -- This query will select all projects where 
FROM Projects      -- ID is not on the list of the subquery 
WHERE ID NOT IN          
     (SELECT ProjectID     -- This subquery will get all 
      FROM Tasks       -- ProjectID who has INCOMPLETE 
      WHERE TaskStatus <> 'COMPLETE')  -- taskStatus 
関連する問題