PHP加速器APC除了缓存字节码,还有一个很重要的应用就是 apc_store, 通常会将配置信息使用apc 缓存起来,更多时候是我们发现配置信息的数组太大了,才考虑将整个数组使用apc缓存起来。
下面我们明确一点基本的知识: apc缓存PHP的数组是序列化之后存储的,
下面我们做一个测试:
测试代码:
- <?php
- test_exec_code();
- test_unserialize();
- test_apc_fetch_arr();
- test_apc_fetch_str();
- test_apc_fetch_str_then_unserialize();
- function test_exec_code() {
- $s = microtime(1);
- while($i++<1000) {
- $arr = getData();
- }
- echo "exec time:", microtime(1) – $s , "s\n";
- }
- function test_unserialize() {
- $arr = getData();
- $str = serialize($arr);
- $s = microtime(1);
- $i = 0;
- while($i++<1000) {
- $arr = unserialize($str);
- }
- echo "unserialize time:", microtime(1) – $s , "s\n";
- }
- function test_apc_fetch_arr() {
- $arr = getData();
- apc_store("arr", $arr);
- $s = microtime(1);
- $i = 0;
- while($i++<1000) {
- $arr = apc_fetch("arr");
- }
- echo "apc_fetch_arr time:", microtime(1) – $s , "s\n";
- }
- function test_apc_fetch_str() {
- $arr = getData();
- $str = serialize($arr);
- apc_store("str", $str);
- $s = microtime(1);
- $i = 0;
- while($i++<1000) {
- $str = apc_fetch("str");
- }
- echo "apc_fetch_str time:", microtime(1) – $s , "s\n";
- }
- function test_apc_fetch_str_then_unserialize() {
- $arr = getData();
- $str = serialize($arr);
- apc_store("str", $str);
- $s = microtime(1);
- $i = 0;
- while($i++<1000) {
- $str = apc_fetch("str");
- $arr = unserialize($str);
- }
- echo "apc_fetch_str_then_unserialize time:", microtime(1) – $s , "s\n";
- }
- function getData() {
- $arr = array(
- ‘220.181.7.41’,
- ‘113.5.32.130’,
-
- );
- return $arr;
- }
|
<?php test_exec_code(); test_unserialize(); test_apc_fetch_arr(); test_apc_fetch_str(); test_apc_fetch_str_then_unserialize(); function test_exec_code() { $s = microtime(1); while($i++<1000) { $arr = getData(); } echo "exec time:", microtime(1) - $s , "s\n"; } function test_unserialize() { $arr = getData(); $str = serialize($arr); $s = microtime(1); $i = 0; while($i++<1000) { $arr = unserialize($str); } echo "unserialize time:", microtime(1) - $s , "s\n"; } function test_apc_fetch_arr() { $arr = getData(); apc_store("arr", $arr); $s = microtime(1); $i = 0; while($i++<1000) { $arr = apc_fetch("arr"); } echo "apc_fetch_arr time:", microtime(1) - $s , "s\n"; } function test_apc_fetch_str() { $arr = getData(); $str = serialize($arr); apc_store("str", $str); $s = microtime(1); $i = 0; while($i++<1000) { $str = apc_fetch("str"); } echo "apc_fetch_str time:", microtime(1) - $s , "s\n"; } function test_apc_fetch_str_then_unserialize() { $arr = getData(); $str = serialize($arr); apc_store("str", $str); $s = microtime(1); $i = 0; while($i++<1000) { $str = apc_fetch("str"); $arr = unserialize($str); } echo "apc_fetch_str_then_unserialize time:", microtime(1) - $s , "s\n"; } function getData() { $arr = array( '220.181.7.41', '113.5.32.130', //... 共 9000 个IP ); return $arr; } $arr = array( '220.181.7.41', '113.5.32.130', |
测试结果:
$ php test.php
exec time:5.3702118396759s
unserialize time:7.4545278549194s
apc_fetch_arr time:50.132069826126s
apc_fetch_str time:0.18340110778809s
apc_fetch_str_then_unserialize time:7.9918370246887s
分析:
1. 不做缓存,每次都执行字节码的效率是最高的,大约每次执行需要 5ms 的时间
2. PHP 反序列话的速度也赶不上执行字节码的速度(至少在这种情况下是这样的)
3. 使用apc缓存数组的效率是相当低的, 每次约 50ms,不如不缓存
4. 使用apc缓存字符串的速度还是不错的,这里的数据量约为260KB,fetch一次的时间约0.18ms
5. 如果说apc的序列化和反序列化使用的是php标准的序列化和反序列化函数,则: apc_fetch_arr 的时间应该基本和 apc_fetch_str_then_unserialize time 的时间一样,但是,这里差别太大了,有些不太理解; 如此看来,如果真要使用apc,则最好先显式地序列化然后在存储,fetch后在显式地反序列化一下