導入 インターネット アプリケーションの普及に伴い、膨大なデータの保存とアクセスがシステム設計におけるボトルネック問題となっています。大規模なインターネット アプリケーションの場合、1 日あたり数十億の PV によってデータベースに非常に高い負荷がかかることは間違いありません。これにより、システムの安定性と拡張性に大きな問題が発生しました。データのセグメンテーションとデータ レイヤーの水平拡張を通じて Web サイトのパフォーマンスを向上させることは、アーキテクチャ開発者にとって好ましい方法となっています。
なぜデータセグメンテーションを行うのですか? 上記は、データ セグメンテーションとは何かについての簡単な説明です。読者は、なぜデータ セグメンテーションが必要なのか疑問に思うかもしれません。 Oracle のような成熟した安定したデータベースは、大量のデータの保存とクエリをサポートするのに十分でしょうか?なぜデータスライスが必要なのでしょうか? 確かに、Oracle の DB は非常に成熟しており安定していますが、高額な使用料とハイエンドのハードウェア サポートはすべての企業にとって手頃な価格ではありません。年間使用料が数千万元、ミニコンピュータのハードウェアサポートに数千万元かかることを想像してみてください。平均的な企業がこれを支払う余裕があるでしょうか?たとえ余裕があっても、より優れたソリューション、より水平方向のスケーラビリティに優れたより安価なソリューションがあるなら、なぜそれを選ばないのでしょうか? 各マシンがどれだけ適切に構成されていても、物理的な限界があることはわかっています。そのため、アプリケーションが 1 台のマシンの特定の限界に達するか、それをはるかに超えると、他のマシンの助けを求めるか、ハードウェアをアップグレードし続けるしかありません。ただし、一般的な解決策は、負荷を分散するためにマシンを追加して水平に拡張することです。また、ビジネス ロジックが拡大し続けるにつれて、マシンが線形成長を通じて需要を満たすことができるかどうかも考慮する必要があります。シャーディングにより、コンピューティング、ストレージ、I/O を複数のマシンに並列に簡単に分散できるため、単一障害点を回避し、システムの可用性を向上させ、エラーを適切に分離しながら、複数のマシンのさまざまな処理機能を最大限に活用できます。 上記の要素を考慮すると、データのセグメンテーションが必要になります。 無料の MySQL と安価なサーバー、または PC を使用してクラスターを構築し、ミニコンピューター + 大規模な商用 DB の効果を実現し、多くの資本投資を削減して運用コストを削減します。なぜそうしないのでしょうか? 大規模および中規模のプロジェクトでは、データベースを設計する際に、データベースが保持できるデータの最大量を考慮して、通常、データベースまたはデータ テーブルは水平に分割され、単一のデータベースまたは単一のテーブルへの負荷が軽減されます。ここでは、2 つのプロジェクトで一般的に使用されるデータ テーブルのセグメンテーション方法を紹介します。もちろん、これらの方法はすべてプログラム内にありますか? 特定のテーブルにルーティングするには、特定のテクニックを使用します。まず、水平分割の基準となるものを確認する必要があります。当社のシステム (SNS) では、ユーザーの UID はシステムを通じて実行され、一意で自動的に増加します。このフィールドに従ってテーブルを分割するのが最適です。 方法1: MD5ハッシュを使用する この方法は、UID を md5 で暗号化し、最初の数桁 (ここでは最初の 2 桁) を取得して、異なる UID を異なるユーザー テーブル (user_xx) にハッシュするというものです。 関数 getTable( $uid ){ $ext = substr(md5($uid),0,2); "user_".$ext を返します。 } このトリックを使用すると、異なる UID を 256 個のユーザー テーブル (user_00、user_01...user_ff) に分散できます。 UID は数値であり増加するため、md5 アルゴリズムに従って、ユーザー データを異なるユーザー テーブルにほぼ均等に分散できます。 しかし、ここで問題があります。システムのユーザー数が増えていくと、1 つのテーブル内のデータ量は必然的に大きくなり、このアルゴリズムに従ってテーブルを拡張することができなくなり、記事の冒頭の問題に戻ってしまいます。 方法2: シフトを使用する 具体的な方法は次のとおりです。 パブリック関数 getTable( $uid ) { "user_" を返します。sprintf( "d", ($uid >> 20) ); } ここで、uid を 20 ビット右にシフトして、最初の 100 万程度のユーザー データを最初のテーブル user_0000 に、次の 100 万のユーザー データを 2 番目のテーブル user_0001 に格納できるようにします。ユーザー数が増えた場合は、ユーザー テーブルを追加するだけで済みます。予約するテーブル サフィックスは 4 桁なので、ここでは user_0000、user_0001...user_9999 という 10,000 個のユーザー テーブルを追加できます。 10,000 個のテーブルと各テーブルに 100 万個のデータがある場合、100 億のユーザー レコードを保存できます。もちろん、ユーザー データがこれより多い場合は問題ありません。拡張可能なテーブルを追加するには、予約済みのテーブル サフィックスを変更するだけです。たとえば、データ項目が 1,000 億あり、各テーブルに 100 万が格納されている場合は、100,000 個のテーブルが必要です。テーブル サフィックスは 6 桁のままにしておくだけで済みます。 上記のアルゴリズムは、より柔軟に記述できます。 /** * UID パーティショニング アルゴリズムに基づく* @param int $uid // ユーザー ID * @param int $bit //テーブルサフィックスに予約されているビット数* @param int $seed //右にシフトするビット数*/ 関数 getTable( $uid , $bit , $seed ){ "user_" を返します。sprintf( "%0{$bit}d" , ($uid >> $seed) ); } まとめ 上記の両方の方法では、現在のシステム内のユーザー データの量を可能な限り推定し、データベース内の 1 つのテーブルが処理できる最大負荷を推定する必要があります。 たとえば、2 番目のソリューションでは、システムのユーザーが 100 億人いて、1 つのテーブルに最適なデータ量が 100 万であると見積もった場合、各テーブルに 100 万のデータが含まれるように UID を 20 ずつ移動し、ユーザー テーブルの 4 桁 (user_xxxx) を保持して 10,000 テーブルに拡張する必要があります。 もう 1 つの例は、最初のソリューションです。各テーブルに 100 万のデータがあり、最初の 2 桁が MD5 に従って取得される場合、テーブルは 256 個だけになります。システムの合計データベースは、256 * 100 万です。システムの合計データ量がこれを超える場合は、MD5 を使用して最初の 3 桁、4 桁、またはそれ以上の桁を取得する必要があります。 どちらの方法でも、データを水平に分割して異なるテーブルに格納します。最初の方法と比較すると、2 番目の方法の方がスケーラビリティに優れています。 要約する 以上がこの記事の全内容です。この記事の内容が皆様の勉強や仕事に何らかの参考学習価値をもたらすことを願います。123WORDPRESS.COM をご愛顧いただき、誠にありがとうございます。これについてもっと知りたい場合は、次のリンクをご覧ください。 以下もご興味があるかもしれません:
|
<<: Nginx ロケーション設定(ロケーションのマッチング順序)の詳細な説明
>>: Node.js管理ツールnvmの詳細なインストール手順
この記事では、タブ切り替えの虫眼鏡効果を実現するためのVueの具体的なコードを例として紹介します。具...
目次概要1. アプリケーションレベルのミドルウェア2. 組み込みミドルウェア3. サードパーティミド...
1. Centosイメージを使用してローカルのyumソースをビルドするCentOS をインストール...
1. フォントと文字表示の関係左側と右側の鋭角部分は Songti フォントで表示されます: &l...
最初で最も重要なステップは、Windows 環境に Ngnix サービスをインストールする方法です。...
この記事では、最新バージョンの MySQL データベース、つまり MySQL 5.7.17 圧縮バー...
CSS レイアウト - position プロパティposition 属性は、要素に適用する配置方法...
序文vsftp は使いやすく安全な FTP サーバー ソフトウェアです。システムユーザーまたは仮想ユ...
目次1. JSONとは何か1.1 配列リテラル1.2 オブジェクトリテラル1.3 混合リテラル1.4...
1. 単一の矢印への複数の呼び出し単一の矢印を実装したら、二重矢印を実装するのは簡単です。上では、単...
序文開発プロセスでは、10 進データ型がよく使用されます。 MySQL では、小数点は正確なデータ型...
目次MySQL の基本的な共通コマンド1. SQL文2. テーブルを作成する3. フィールドのプロパ...
目次目的モジュールのインストール基本的な使い方ポートをスキャンする開いているポートデータの送信データ...
序文今日 GitHub を閲覧していたところ、SQL を最適化および書き換えるための sora とい...
目次ブートストラップと関連コンテンツの紹介グリッドシステムネストされた列列オフセット列の並べ替えナビ...