2

背景:私は自分の画像のコレクションを管理するための自作プロジェクトに取り組んでおり、タグベースの検索を実装して、それらを簡単にふるいにかけることができるようにしようとしています。

現在、各画像のデータベースエントリにタグを適用するためにRedBeanのタグ付けAPIを使用していますが、実装の特定の詳細に固執しています。現在、複数のタグで検索を絞り込むタグの検索を許可するには(「ABC XYZ」を検索する場合、タグ付き画像には「ABC」「XYZ」のタグが必要です)、

SQLではなくサーバー側の言語で処理の一部を処理し、(オプションの)2番目のクエリを実行して、返された画像に結果から明示的に除外されたタグがないことを確認する必要があります。(「ABC-XYZ」を検索する場合、タグ付けされた画像には「XYZ」ではなく「ABC」のタグが必要です)。

ここでの問題は、現在の方法では、サーバー側のコードですべての結果を実行する必要があり、適切なページ付け/結果オフセットの試行が不正確になることです。

私の目標はpost、要求されたタグを含む(除外されたタグを含まない)テーブルの行を1つのクエリで取得し、クエリにLIMIT / OFFSET引数を使用して、適度にページ分割された結果を取得できるようにすることです。

テーブルスキーマは次のとおりです。

Table "post"
Columns:
  id (PRIMARY KEY for post table)
  (image metadata, not relevant to tag search)

Table "tag"
Columns:
  id (PRIMARY KEY for tag table)
  title (string of varying length - assume varchar(255))

Table "post_tag"
Columns:
  id (PRIMARY KEY for post_tag table)
  post_id (associated with column "post.id")
  tag_id (associated with column "tag.id")

post可能であれば、テーブル列に固有のWHERE条件も設定できるようにしたいと思います。

クエリ構造には何を使用する必要がありますか?私は左結合で遊んでいますが、これを解決するために必要な正確な構造を取得できませんでした。

4

1 に答える 1

2

基本的な考え方は次のとおりです。

LEFT OUTER JOIN、除外するタグに一致する投稿のセットです。クエリの最後の句は、これらの投稿のいずれも最初のテーブルWHEREのエントリと一致しないことを確認します。post

INNER JOIN、すべてのタグに一致する投稿のセットです。IN2番目の数字は、句で指定する一意のタグ名の数と一致する必要があることに注意してください。

select p.*
from post p
left outer join (
    select pt.post_id    
    from post_tag pt
    inner join tag t on pt.tag_id = t.id
    where t.title in ('UVW', 'XYZ')
) notag on p.id = notag.post_id 
inner join (
    select pt.post_id    
    from post_tag pt
    inner join tag t on pt.tag_id = t.id
    where t.title in ('ABC', 'DEF')
    group by pt.post_id
    having count(distinct t.title) = 2
) yestag on p.id = yestag.post_id 
where notag.post_id is null
--add additional WHERE filters here as needed
于 2012-04-17T16:27:36.670 に答える