php - 将PHP存储数组( json_encode VSserialize) 首选方法

  显示原文与译文双语对照的内容

我需要在平面文件中存储一个multi-dimensional关联数组,用于缓存目的。 我可能偶尔会遇到需要把它转换成json用于web应用程序,但绝大多数的时间我将使用直接在php数组。

将数组作为JSON或者PHP序列化数组存储在这里文本文件中是否更有效? 我环顾四周,似乎在最新版本的php( 5.3 ) json_decode 实际上是比 unserialize 快。

我现在倾向于存储数组作为json作为其容易被人类阅读我觉得如果有必要,它既可以用在php和javascript用很少的努力,和我读过,它甚至可能更快( 虽然不确定编码,但) 解码。

谁知道有什么陷阱? 任何人都有良好的基准来显示任何一种方法的性能优势?

时间:

取决于你的优先级。

如果性能是你的绝对驾驶特征,那么无论如何使用最快的。 在做出选择之前,请确保你对这些差异有充分的理解

  • 默认情况下,json_encode() 将UTF-8字符转换为Unicode转义序列,而 serialize() 不。 注意:离开UTF-8字符不变,你可以使用php 5.4 JSON_UNESCAPED_UNICODE 选项。
  • JSON对对象类的原始内容没有内存。
  • 你不能利用 __sleep()__wakeup() 来使用 JSON
  • 只有公共属性用JSON序列化
  • JSON更便携

还有一些其他的区别我现在无法考虑。

用于比较两者的简单速度测试


<?php

ini_set( 'display_errors', 1 );
error_reporting( E_ALL );

//Make a bit, honkin test array
//You may need to adjust this depth to avoid memory limit errors
$testArray = fillArray( 0, 5 );

//Time json encoding
$start = microtime( true );
json_encode( $testArray );
$jsonTime = microtime( true ) - $start;
echo"JSON encoded in $jsonTime seconds<br>";

//Time serialization
$start = microtime( true );
serialize( $testArray );
$serializeTime = microtime( true ) - $start;
echo"PHP serialized in $serializeTime seconds<br>";

//Compare them
if ( $jsonTime <$serializeTime )
{
 echo"json_encode() was roughly". number_format( ($serializeTime/$jsonTime - 1 ) * 100, 2 )."% faster than serialize()";
}
else if ( $serializeTime <$jsonTime )
{
 echo"serialize() was roughly". number_format( ($jsonTime/$serializeTime - 1 ) * 100, 2 )."% faster than json_encode()";
} else {
 echo 'Unpossible!';
}

function fillArray( $depth, $max )
{
 static $seed;
 if ( is_null( $seed ) )
 {
 $seed = array( 'a', 2, 'c', 4, 'e', 6, 'g', 8, 'i', 10 );
 }
 if ( $depth <$max )
 {
 $node = array();
 foreach ( $seed as $key )
 {
 $node[$key] = fillArray( $depth + 1, $max );
 }
 return $node;
 }
 return 'empty';
}

JSON更简单和更快的比应该使用序列化php格式和除非 :

  • 你正在存储嵌套的嵌套数组: json_decode() :"这个函数将 return false 如果json编码的数据比 127元素。"
  • 你正在存储需要是非宿主的对象作为正确的类
  • 你正在与不支持json_decode的旧PHP版本交互

你刚刚测试了序列化和json编码和解码,以及将字符串存储的大小。


JSON encoded in 0.067085981369 seconds. Size (1277772)
PHP serialized in 0.12110209465 seconds. Size (1955548)
JSON decode in 0.22470498085 seconds
PHP serialized in 0.211947917938 seconds
json_encode() was roughly 80.52% faster than serialize()
unserialize() was roughly 6.02% faster than json_decode()
JSON string was roughly 53.04% smaller than Serialized string

我们可以得出结论,JSON编码速度更快,结果更小,但是unserialize更快解码字符串。

我增加了测试以包括unserialization性能。 下面是我得到的数字。


Serialize

JSON encoded in 2.5738489627838 seconds
PHP serialized in 5.2861361503601 seconds
Serialize: json_encode() was roughly 105.38% faster than serialize()


Unserialize

JSON decode in 10.915472984314 seconds
PHP unserialized in 7.6223039627075 seconds
Unserialize: unserialize() was roughly 43.20% faster than json_decode()

所以json的编码速度快,但解码速度较慢。 所以它可能取决于你的应用程序以及你期望做什么。

我已经测试了这个非常彻底的一个相当复杂的,温和的嵌套 multi-hash ( 字符串,空,整数) 和各种各样的数据,最后系列化/非系列化比 json_encode/json_decode快得多。

在我的测试中,json的唯一优势是它的'已经打包'大小较小。

这些是在 PHP 5.3.3下完成的,如果你想要更多的细节,请告诉我。

下面是测试结果,然后是生成它们的代码。 我不能提供测试数据,因为它揭示了我不能在野外出去的信息。


JSON encoded in 2.23700618744 seconds
PHP serialized in 1.3434419632 seconds
JSON decoded in 4.0405561924 seconds
PHP unserialized in 1.39393305779 seconds

serialized size : 14549
json_encode size : 11520
serialize() was roughly 66.51% faster than json_encode()
unserialize() was roughly 189.87% faster than json_decode()
json_encode() string was roughly 26.29% smaller than serialize()

//Time json encoding
$start = microtime( true );
for($i = 0; $i <10000; $i++) {
 json_encode( $test );
}
$jsonTime = microtime( true ) - $start;
echo"JSON encoded in $jsonTime seconds<br>";

//Time serialization
$start = microtime( true );
for($i = 0; $i <10000; $i++) {
 serialize( $test );
}
$serializeTime = microtime( true ) - $start;
echo"PHP serialized in $serializeTime seconds<br>";

//Time json decoding
$test2 = json_encode( $test );
$start = microtime( true );
for($i = 0; $i <10000; $i++) {
 json_decode( $test2 );
}
$jsonDecodeTime = microtime( true ) - $start;
echo"JSON decoded in $jsonDecodeTime seconds<br>";

//Time deserialization
$test2 = serialize( $test );
$start = microtime( true );
for($i = 0; $i <10000; $i++) {
 unserialize( $test2 );
}
$unserializeTime = microtime( true ) - $start;
echo"PHP unserialized in $unserializeTime seconds<br>";

$jsonSize = strlen(json_encode( $test ));
$phpSize = strlen(serialize( $test ));

echo"<p>serialized size :". strlen(serialize( $test ))."<br>";
echo"json_encode size :". strlen(json_encode( $test ))."<br></p>";

//Compare them
if ( $jsonTime <$serializeTime )
{
 echo"json_encode() was roughly". number_format( ($serializeTime/$jsonTime - 1 ) * 100, 2 )."% faster than serialize()";
}
else if ( $serializeTime <$jsonTime )
{
 echo"serialize() was roughly". number_format( ($jsonTime/$serializeTime - 1 ) * 100, 2 )."% faster than json_encode()";
} else {
 echo 'Unpossible!';
}
 echo '<BR>';

//Compare them
if ( $jsonDecodeTime <$unserializeTime )
{
 echo"json_decode() was roughly". number_format( ($unserializeTime/$jsonDecodeTime - 1 ) * 100, 2 )."% faster than unserialize()";
}
else if ( $unserializeTime <$jsonDecodeTime )
{
 echo"unserialize() was roughly". number_format( ($jsonDecodeTime/$unserializeTime - 1 ) * 100, 2 )."% faster than json_decode()";
} else {
 echo 'Unpossible!';
}
 echo '<BR>';
//Compare them
if ( $jsonSize <$phpSize )
{
 echo"json_encode() string was roughly". number_format( ($phpSize/$jsonSize - 1 ) * 100, 2 )."% smaller than serialize()";
}
else if ( $phpSize <$jsonSize )
{
 echo"serialize() string was roughly". number_format( ($jsonSize/$phpSize - 1 ) * 100, 2 )."% smaller than json_encode()";
} else {
 echo 'Unpossible!';
}

在做出最终决策之前,请注意,JSON格式对于关联数组是不安全的- json_decode() 将作为对象返回它们:


$config = array(
 'Frodo' => 'hobbit',
 'Gimli' => 'dwarf',
 'Gandalf' => 'wizard',
 );
print_r($config);
print_r(json_decode(json_encode($config)));

输出是:


Array
(
 [Frodo] => hobbit
 [Gimli] => dwarf
 [Gandalf] => wizard
)
stdClass Object
(
 [Frodo] => hobbit
 [Gimli] => dwarf
 [Gandalf] => wizard
)

...