7

私はウェブショップタイプのアプリケーションに取り組んでいます。他のWebサイトでよく見られる機能の1つは、フィルタリングオプションの内訳であり、その後、そのフィルタリングオプションの結果の合計数になります。これは、コンピューターサイト(Neweggなど)や中古車サイトでよく見られます。例:

CPU:
  * AMD (315)
  * Intel (455)

Video card:
  * ATI (378)
  * Nvidia (402)

これらの合計を効率的に計算するにはどうすればよいですか?私が取り組んでいるWebサイトには、さまざまなオプションを備えたさまざまな製品(10.000以上)があります。さらに悪いことに、製品は絶えず変化しています。

さまざまなフィルタリングの組み合わせの合計をすべて事前に計算しようとするのは実行不可能のようです。それぞれ4つのオプションを持つ5つの異なるフィルターがある場合、オプションの可能性の数はになります20 * 16 * 12 * 8 * 4 = 122880。それを計算するには長い時間がかかります。

もう1つのオプションは、オンデマンドでクエリを実行し、結果をキャッシュすることです(Redisなど)。しかし、製品が追加および削除され続ける場合、どうすればキャッシュを効率的に管理できますか?多くの場合、キャッシュは古くなっています。どういうわけか、キャッシュの無効化を細かく管理する必要があり、非常に複雑で脆弱な実装につながるのではないかと心配しています。別の方法は、キャッシュの幅広いセクションを無効にすることです。しかし、無効にした直後、私のデータベースは、これらの合計を再計算する必要があるアクティブユーザーからの大量のクエリによって急いでいました。

これを処理するための素敵でエレガントな方法はありますか?

4

2 に答える 2

3

あなたのケースのライブデータを表示しても問題はありません。決してあなたを落胆させることはありませんが、10K製品はそれほど多くはなく、パフォーマンスの面でも優れています。一方、数百万はそうです。

実際にこの方法で実装しようとしたところ、パフォーマンスが遅いことがわかりましたか、それとも理論上のパフォーマンスを意識しすぎていませんか?現状のままシステムでストレステストを行い、改善する価値があるかどうかを確認することをお勧めします。それでも、それをより速くするためのいくつかのアイデアがあります:

  1. 特定のカテゴリが展開/クリックされた場合にのみ、すべてのカウントを一度に入力しないでください。したがって、常に1つのSELECT cat_name, COUNT(*) GROUP BY cat_nameクエリで終了しますが、それほど時間はかかりません。ユーザークリックごとのこのような単一の比較的軽いクエリは、私にとって合理的に聞こえます。

  2. データベースエンジンにキャッシュを管理させます。同様のクエリを頻繁に実行する場合、データベースエンジンは、基盤となるストレージを自動的に最適化する必要があります(つまり、テーブル全体をメモリなどに移動します)。インスタンスに十分なメモリがあることを確認する必要があります。

  3. 必要に応じて、サーバーハードウェアをアップグレードします。データ量が増えると、すべてを保存するのに十分なメモリがない可能性があります。まだ慌てる必要はありません。ボトルネックの場所に応じて、SSDを挿入したり、12コアのXeonプロセッサをサーバーにインストールしたりできます。

于 2012-11-04T19:49:20.193 に答える
0

他の方法で考えて、データベースに数値を保持するのはどうですか?商品が特定のカテゴリに追加/削除された場合に、トリガーを使用してカウンターを自動的にインクリメント/デクリメントすることができます(そうでない場合でも、ストアマネージャーが販売中の商品を追加/削除できるダイアログで明示的に処理できます) 。

これは良い解決策のように思われます。なぜなら、a)カテゴリの名前はすでにDBに保存されているので、番号を尋ねるのにかかるオーバーヘッドはごくわずかであり、b)製品は絶えず変化しているにもかかわらず、多くの場合、変化している可能性が高いからです。リクエストの頻度よりも低い頻度(ユーザー自身が製品を追加/削除できる場合でも保持されます)。そして最後にc)複雑なキャッシュスキームはなく、カウンターはコードの単一の部分によって単一の場所で管理されています。エラーのない状態を維持するのは簡単なはずです。

于 2012-11-04T19:21:16.067 に答える