50/50の挿入と選択。 2つのテーブルまたは1つのテーブルを作成します
-
26-10-2019 - |
質問
今、提案されたテーブル構造は次のとおりです。
data_table
->impressions
->clicks
->ctr
また
data_table_1
->ctr
data_table_2
->impressions
->clicks
どのクエリが実行されますか?インプレッションには約500秒あたりの更新があります。毎秒クリックするために約1つの更新があります。 CTRには、1秒あたり約500の更新があります。
これで、アプリケーションはCTRを使用してデータをソートします。 CTRはクリックスルーレートです。 ctr = clicks/impressions
. 。クリックの更新がない限り、CTRは、同じ関係でCTRが減少している記事のすべての印象が増加しているため、CTRを更新する必要がないことに気付きました。更新します。
現在、更新クエリは「data_tableの更新=インプレッション=インプレッション + 1、ctr =クリック /インプレッションがある場所=何か=何かのようなものです。
これは、2つのフィールドが一度に更新されますが、1つのクエリのみが実行されることを意味します。
これで、ボトルネックは、これらの500の更新により、このテーブルの選択が遅くなります。約20秒あたりの選択があります。だから私はテーブルを分離することを考えました。新しいテーブルスタイルは、更新が別のテーブルで行われ、選択が別のテーブルで発生することを提案しています。インプレッションを含むデータテーブルは非常に頻繁に更新されるため、インプレッションの更新を実行することで、このテーブルのパフォーマンスが実際に高速化されます。これは、data_table_2のselectsがより速くなり、誰かがクリックするたびにCTRを更新できることを意味します。
だから、新しいテーブル構造を使用するかどうかを知りたかっただけです。あなたは何を提案していますか?私の提案の長所と短所!
解決
たぶんこれはあなたの質問に対する直接的な答えではありませんが、注意することは重要だと思います。
Redis、MemCachedB、MongDB、CouchDBなどのNOSQLデータベースの使用を検討する必要があると思います。相対的なDBMは、この種の使用に適していません。たとえば、列を更新するたびに(UPDATE data_table SET impressions = impressions + 1
)キャッシュは消去され、DBはディスクにヒットする必要があります。
他には、MemcacheとBulkを使用してデータを使用することです。
たとえば、いくつかの感情を失う余裕がある場合(Memcacheはデータを持続しないことを忘れないでください)、Memcacheでインペレーション++を実行し、5分ごとにDBでデータを更新できます。負荷が大幅に減少します。
それがあなたを助けることを願っています。
編集:
CTRの保存は良いアイデアであり、「非正規化」と呼ばれ、頻繁に必要な値であればアプリケーションで機能する可能性があります。
他のヒント
まず第一に、私はテーブルが十分に索引付けされているので、 something = something
述語はすぐに対応する行になりますよね?
さらに高い更新レートのためにボトルネックがディスクスループットであると仮定すると、CTR値をまったく保存しないことはどうですか?更新によって制限されているように見えるため、1つのフィールドのみを更新するだけで、ディスクにデータを書き込む必要があるという影響の約半分が必要です。 CPUがおそらく比較的アイドル状態であるこのようなシナリオを考えると、すべての結果のクリック/インプレッションを計算することは問題ではないはずです。あなたのアプローチは報われます(ディスクが制限要因であると仮定すると、CPUの使用率を見ることで簡単に見つけることができると仮定します)、あなたのアプローチはかなりの利点を与えます、 iff テーブルまたは2つの異なるディスク上。
CPUが制限要因であることが判明した場合、それはおそらく something = something
述語は、これを単純化することが主な関心事であり、テーブルを分割しないことを評価するのに非常に複雑です。