web-dev-qa-db-ja.com

タグをデータベースに保存する最も効率的な方法は何ですか?

私は私のstackoverflowの使用に似たタグシステムを私のウェブサイトに実装していますが、私の質問は-タグを検索してフィルタリングできるようにタグを保存する最も効果的な方法は何ですか?

私の考えはこれです:

Table: Items
Columns: Item_ID, Title, Content

Table: Tags
Columns: Title, Item_ID

これは遅すぎますか?もっと良い方法はありますか?

131
Logan Serman

1つのアイテムには多くのタグがあります。そして、1つのタグが多くのアイテムに属します。これは、多対多の障害を克服するために、おそらく中間テーブルが必要になることを意味します。

何かのようなもの:

表:アイテム
列:Item_ID、Item_Title、Content

表:タグ
列:Tag_ID、Tag_Title

テーブル:Items_Tags
列:Item_ID、Tag_ID

あなたのウェブアプリはめちゃくちゃ人気があり、道を非正規化する必要があるかもしれませんが、それはあまりにも早く水を濁している意味がありません。

181
Simon Scarfe

データベーススキーマのタグ付けに関するPhilipp Kellerのブログ投稿を読む必要があります。 一般的なクエリの構築のしやすさの項パフォーマンスの点 の両方で、彼はいくつか試して結果を報告します。タグの数、タグ付きアイテムの数、およびアイテムごとのタグの数がすべての要因でした。投稿は2005年のものです。それ以降の更新については知りません。

106
Rob Kennedy

実際、規模に応じて、タグテーブルを非正規化する方が前向きな方法であると考えています。

このように、タグテーブルには単純にtagid、itemid、tagnameがあります。

タグ名は重複しますが、特定のアイテムのタグの追加/削除/編集が非常に簡単になります。新しいタグを作成し、古いタグの割り当てを削除して新しいタグを再割り当てする必要はありません。タグ名を編集するだけです。

タグのリストを表示するには、単にDISTINCTまたはGROUP BYを使用します。もちろん、タグが簡単に使用された回数もカウントできます。

7
Neil Barnwell

非標準的なものを少し使用してもかまわない場合、Postgresバージョン9.4以降には、JSONテキスト配列タイプのレコードを保存するオプションがあります。

スキーマは次のようになります。

Table: Items
Columns: Item_ID:int, Title:text, Content:text

Table: Tags
Columns: Item_ID:int, Tag_Title:text[]

詳細については、Josh Berkusによる次の優れた投稿を参照してください。 http://www.databasesoup.com/2015/01/tag-all-things.html

パフォーマンスに関して徹底的に比較されたさまざまなオプションがあり、上記で提案されたものが全体的に最適です。

3
Dmitry Shvedov

タグとアイテムの間に多対多の関係があるため、つまり、1つのアイテムを複数のタグに関連付けることができ、1つのタグを複数のアイテムに関連付けることができるため、tags <=>アイテムの関連付けを格納するために中間の3番目のテーブルを使用することをお勧めします。 HTH、バルブ。

2
Valentin

質問で提供したデータに基づいて遅さについて話すことはできません。そして、開発のこの段階でのパフォーマンスについてあまり心配する必要はないと思います。 時期尚早の最適化 と呼ばれます。

ただし、TagsテーブルにTag_ID列を含めることをお勧めします。通常、すべてのテーブルにID列があることをお勧めします。

1
Rockcoder

スペースが問題になる場合は、タグのテキストを保存する3番目のテーブルTags(Tag_Id、Title)を用意し、Tagsテーブルを(Tag_Id、Item_Id)に変更します。これらの2つの値は、一意の複合主キーも提供する必要があります。

1
Adam Pope

アイテムには「ID」フィールドが必要で、タグには「ID」フィールド(プライマリキー、クラスター化)が必要です。

次に、ItemID/TagIDの中間テーブルを作成し、そこに「 Perfect Index 」を配置します。

0
Timothy Khouri