「ひとつのキーに、まとめてデータを入れるとオーバーヘッドがかかるかもしれないよ」
と教えられ、現在ひとつのキーに入れないような設計をしている最中で、
じゃあ、試しに、1,000の値 を、
- ひとつのキーに全データをシリアライズして入れる
- 1,000のキーとして入れる
というそれぞれの方法では、実際にどれだけオーバーヘッドの可能性があるかどうか。
ターゲットは wp_options
オーバーヘッドは一切ありません。
ここで挿入する値の定義
1,000個の1~10,000,000の乱数を作成して挿入
つまり、
array( 0 => 2384、093, 1 => 6923230, 2 => 8053892, ... 999 => 1034544 );
のようなデータです。
データには日本語や英文が入る場合が多いので、今回はデータ量が少ない気がして、
良いテストかどうかと聞かれれば、分かりません。としか答えられませんが、
少しぐらいは何か分かるのではないかと思い、やってみることにしました。
wp_options にまずは、ひとつのキーに1,000の配列を挿入することを仮定して、試してみました。
$SampleData = array(); for( $i=0; $i<1000; $i++ ) { $SampleData[$i] = rand( 1 , 1000000 ); } print_r($SampleData);
print_r で値を確認。1,000の配列が出来ています。
これを、wp_optionsへひとつのキーとして、シリアライズしたデータをupdate_optionで挿入してみると、
ぎっしりはいりました。結果…
オーバーヘッドはなし。
えっ? これじゃ検証にならない。。もっとデータ量を増やして試してみよう。
ということで、オーバーヘッドされるまで、データ量を増やしながら色々と試行錯誤…。
結果。どんなに頑張ってもオーバーヘッドしなかった。。
参ったなぁ。指摘されているから、オーバーヘッドするはずなんだけど…
実際にオーバーヘッドしているテーブルがあったので、そのテーブルとひたすらにらめっこ。
すると、気づきました…。
MyISAM
ん?「MyISAM」?私のイサム?メルティーラブ??
軽めにググってみました。
あ、データベースにも色々とデータの種類があるのね。全く知りませんでした。
で、さっそくテスト環境に使っているテーブルの型を、MyISAMに変更。
同じように1,000個の値を持つ乱数配列で再度update_optionでデータを挿入すると…
でました。オーバーヘッド。
ひとつのキーに、1,000個の、乱数で作成された値をもつ配列を、シリアライズして挿入すると、
29.5 KiB (KiBって何?キロバイトじゃなくて?)
計10回、挿入してみましたが、 29.5 KiBから変わらなかったです。
なるほど。何度も値を挿入しても、値は変わらないのか。配列の値も色々と変えてみる。
ここまでで分かったこと
× 1回のオーバーヘッド量 29.5 KiB × 10回updateすると = 295KiB になるわけではなく、
○ 挿入するデータ量に応じて、オーバーヘッドのサイズが変わる。何度更新しても。
そっか。
これじゃあ何度テーブルの最適化をしても、そのupdateをする限りいつまでもオーバーヘッドするじゃないか。
よし。
次の検証にうつります。その前に、オーバーヘッドの最適化。
次は、1,000のキーとして、値を挿入。の検証
挿入するデータは以下。
for( $i=0; $i<1000; $i++ ) {
update_option( 'sampledata' . $i , rand( 1 , 1000000 ) );
}
結果は。オーバーヘッドなし
確かにこの方法がいいかもしれない。
ん?ちょっとここでもうひとつ試してみることにしました。
update_optionの値を、ただの配列にするとどうなるか
for( $i=0; $i<1000; $i++ ) { update_option( 'sampledata' . $i , array( rand( 1 , 1000000 ) ) ); }
結果はこちら。
20 バイト。配列にするだけで、オーバーヘッドが起こるのか。
wordpress の update_option()の流れとしては(ざっくり)、
- update_option() の値に配列やオブジェクトをつっこむ
- maybe_serialize()という処理が入る
この”たぶん、シリアライズ機能”のほうで、
if ( is_array( $data ) || is_object( $data ) ) return serialize( $data );
シリアライズされたデータを返し、データベースのデータが更新されます。
じゃあ、配列でupdate_optionデータを更新する限り、シリアライズされる。
シリアライズされたデータで、 データベースの型が MyISAM なら、ほぼオーバーヘッドが起こる。
(データベースの環境も左右されるかもしれませんね)
いい勉強になりました。
オーバーヘッドを避ける為には、1キーに1つの値。
という事ですね。
今公開中のプラグインは、ほとんどがシリアライズされたデータなので、いくつかは変更する予定です。
>>追記
実際には、1キー に 1つの値 にしても、オーバーヘッドを避ける事はできませんでした。
どういう事かというと…
作成したキーを、削除するだけでもオーバーヘッドが出ました。
また、コメントでbloger323さんがおっしゃる通り、データの増減が激しい場合もオーバーヘッドが出るようです。
うーん、どういう構造がいいんでしょうね。。
コメントを残す