Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/253.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 检查字符串是否已序列化?_Php_Serialization - Fatal编程技术网

Php 检查字符串是否已序列化?

Php 检查字符串是否已序列化?,php,serialization,Php,Serialization,确定字符串是否是serialize()函数的结果的最佳方法是什么 我想说,试试看;-) 引用手册: 如果传递的字符串不是 不可序列化,返回FALSE并 发出紧急通知 因此,您必须检查返回值是否为false(使用==或!==,以确保0或null或任何等于false的内容都没有问题 请注意注意注意:您可能想要/需要使用 例如: $str = 'hjkl'; $data = @unserialize($str); if ($data !== false) { echo "ok"; } else

确定字符串是否是
serialize()
函数的结果的最佳方法是什么

我想说,试试看;-)

引用手册:

如果传递的字符串不是 不可序列化,返回FALSE并 发出紧急通知

因此,您必须检查返回值是否为
false
(使用
==
!==
,以确保
0
null
或任何等于
false
的内容都没有问题

请注意注意注意:您可能想要/需要使用

例如:

$str = 'hjkl';
$data = @unserialize($str);
if ($data !== false) {
    echo "ok";
} else {
    echo "not ok";
}
将为您提供:

not ok

编辑:哦,就像@Peter所说的(多亏了他!),如果您试图取消布尔false表示的序列化,您可能会遇到麻烦:-(

因此,检查序列化字符串是否不等于“
b:0;
”,可能也会有所帮助;我想,类似这样的操作应该可以实现这一点:

$data = @unserialize($str);
if ($str === 'b:0;' || $data !== false) {
    echo "ok";
} else {
    echo "not ok";
}
在尝试取消序列化之前测试这种特殊情况将是一种优化——但如果您不经常有错误的序列化值,则可能没有那么大的用处

$data = @unserialize($str);
if($data !== false || $str === 'b:0;')
    echo 'ok';
else
    echo "not ok";

正确处理
序列化(false)
:)

尽管帕斯卡·马丁的回答很好,但我很好奇你是否可以用另一种方法来处理这个问题,所以我做这件事只是作为一种心理练习

<?php

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

$valueToUnserialize = serialize( false );
//$valueToUnserialize = "a"; # uncomment this for another test

$unserialized = @unserialize( $valueToUnserialize );

if ( FALSE === $unserialized && isset( $php_errormsg ) && strpos( $php_errormsg, 'unserialize' ) !== FALSE )
{
  echo 'Value could not be unserialized<br>';
  echo $valueToUnserialize;
} else {
  echo 'Value was unserialized!<br>';
  var_dump( $unserialized );
}

优化Pascal MARTIN的反应

/**
 * Check if a string is serialized
 * @param string $string
 */
public static function is_serial($string) {
    return (@unserialize($string) !== false);
}

这段代码不是我写的,实际上是WordPress写的。我想我会把它给任何感兴趣的人,这可能有点过分,但它是有效的:)


如果$string是一个序列化的
false
值,即
$string='b:0;'
SoN9ne的函数返回
false
,这是错误的

所以函数应该是

/**
 * Check if a string is serialized
 *
 * @param string $string
 *
 * @return bool
 */
function is_serialized_string($string)
{
    return ($string == 'b:0;' || @unserialize($string) !== false);
}
这对我来说很好

<?php

function is_serialized($data){
    return (is_string($data) && preg_match("#^((N;)|((a|O|s):[0-9]+:.*[;}])|((b|i|d):[0-9.E-]+;))$#um", $data));
    }

?>

内置到函数中

function isSerialized($value)
{
   return preg_match('^([adObis]:|N;)^', $value);
}

有一个WordPress解决方案:

函数已序列化($data,$strict=true)
{
//如果它不是字符串,则不会序列化。
如果(!是字符串($data)){
返回false;
}
$data=修剪($data);
如果('N;'=$data){
返回true;
}
if(strlen($data)<4){
返回false;
}
如果(“:”!==$data[1]){
返回false;
}
如果($严格){
$lastc=substr($data,-1);
如果(“;”!=$lastc&&“}”!=$lastc){
返回false;
}
}否则{
$semicolon=strpos($data,“;”);
$brace=strpos($data,'}');
//要么;或}必须存在。
if(false==$分号&&false==$brace)
返回false;
//但两者都不必在前X个字符中。
if(false!=$分号&&$分号<3)
返回false;
if(false!=$brace&&$brace<4)
返回false;
}
$token=$data[0];
交换机($token){
案例s:
如果($严格){
如果(“”!==substr($data,-2,1)){
返回false;
}
}elseif(false==strpos($data,“')){
返回false;
}
//否则就会失败
案例“a”:
案例“O”:
return(bool)preg_match(“/^{$token}:[0-9]+:/s”,$data);
案例“b”:
案例“i”:
案例“d”:
$end=$strict?“$”:“”;
return(bool)preg_match(“/^{$token}:[0-9.E-]+;$end/”,$data);
}
返回false;
}

参见wordpress功能

function isSerialized($value)
{
   return preg_match('^([adObis]:|N;)^', $value);
}
函数已序列化($data,$strict=true){
//如果它不是字符串,则不会序列化。
如果(!是字符串($data)){
返回false;
}
$data=修剪($data);
如果('N;'=$data){
返回true;
}
if(strlen($data)<4){
返回false;
}
如果(“:”!==$data[1]){
返回false;
}
如果($严格){
$lastc=substr($data,-1);
如果(“;”!=$lastc&&“}”!=$lastc){
返回false;
}
}否则{
$semicolon=strpos($data,“;”);
$brace=strpos($data,'}');
//要么;或}必须存在。
if(false==$分号&&false==$brace){
返回false;
}
//但两者都不必在前X个字符中。
if(false!=$分号&&$分号<3){
返回false;
}
if(false!=$brace&&$brace<4){
返回false;
}
}
$token=$data[0];
交换机($token){
案例s:
如果($严格){
如果(“”!==substr($data,-2,1)){
返回false;
}
}elseif(false==strpos($data,“')){
返回false;
}
//否则就会失败。
案例“a”:
案例“O”:
return(bool)preg_match(“/^{$token}:[0-9]+:/s”,$data);
案例“b”:
案例“i”:
案例“d”:
$end=$strict?“$”:“”;
return(bool)preg_match(“/^{$token}:[0-9.E+-]+;$end/”,$data);
}
返回false;

}

我会尝试将其取消序列化。这就是我解决问题的方法

公共静态函数已序列化($string)
{
试一试{
取消序列化($string);
}捕获(\异常$e){
返回false;
}
返回true;
}
或者更像一个助手函数

函数已序列化($string){
试一试{
取消序列化($string);
}捕获(\异常$e){
返回false;
}
返回true;
}
  • 所提到的方法并没有真正检测数组(
    a:1:{42}
    被认为是序列化的),并且在转义字符串上错误地返回
    true
    ,如
    a:1:{s:3:\'foo\;s:3:\'bar\;}
    (尽管
    未序列化
    不起作用)

  • 例如,如果在另一侧使用
    @unserialize
    方式,WordPress会在t的顶部添加一个难看的边距
    function isSerialized($value)
    {
       return preg_match('^([adObis]:|N;)^', $value);
    }
    
        function is_serialized($data, $strict = true)
        {
            // if it isn't a string, it isn't serialized.
            if (!is_string($data)) {
                return false;
            }
            $data = trim($data);
            if ('N;' == $data) {
                return true;
            }
            if (strlen($data) < 4) {
                return false;
            }
            if (':' !== $data[1]) {
                return false;
            }
            if ($strict) {
                $lastc = substr($data, -1);
                if (';' !== $lastc && '}' !== $lastc) {
                    return false;
                }
            } else {
                $semicolon = strpos($data, ';');
                $brace = strpos($data, '}');
                // Either ; or } must exist.
                if (false === $semicolon && false === $brace)
                    return false;
                // But neither must be in the first X characters.
                if (false !== $semicolon && $semicolon < 3)
                    return false;
                if (false !== $brace && $brace < 4)
                    return false;
            }
            $token = $data[0];
            switch ($token) {
                case 's' :
                    if ($strict) {
                        if ('"' !== substr($data, -2, 1)) {
                            return false;
                        }
                    } elseif (false === strpos($data, '"')) {
                        return false;
                    }
                // or else fall through
                case 'a' :
                case 'O' :
                    return (bool)preg_match("/^{$token}:[0-9]+:/s", $data);
                case 'b' :
                case 'i' :
                case 'd' :
                    $end = $strict ? '$' : '';
                    return (bool)preg_match("/^{$token}:[0-9.E-]+;$end/", $data);
            }
            return false;
        }
    
    function is_serialized( $data, $strict = true ) {
    // If it isn't a string, it isn't serialized.
    if ( ! is_string( $data ) ) {
        return false;
    }
    $data = trim( $data );
    if ( 'N;' === $data ) {
        return true;
    }
    if ( strlen( $data ) < 4 ) {
        return false;
    }
    if ( ':' !== $data[1] ) {
        return false;
    }
    if ( $strict ) {
        $lastc = substr( $data, -1 );
        if ( ';' !== $lastc && '}' !== $lastc ) {
            return false;
        }
    } else {
        $semicolon = strpos( $data, ';' );
        $brace     = strpos( $data, '}' );
        // Either ; or } must exist.
        if ( false === $semicolon && false === $brace ) {
            return false;
        }
        // But neither must be in the first X characters.
        if ( false !== $semicolon && $semicolon < 3 ) {
            return false;
        }
        if ( false !== $brace && $brace < 4 ) {
            return false;
        }
    }
    $token = $data[0];
    switch ( $token ) {
        case 's':
            if ( $strict ) {
                if ( '"' !== substr( $data, -2, 1 ) ) {
                    return false;
                }
            } elseif ( false === strpos( $data, '"' ) ) {
                return false;
            }
            // Or else fall through.
        case 'a':
        case 'O':
            return (bool) preg_match( "/^{$token}:[0-9]+:/s", $data );
        case 'b':
        case 'i':
        case 'd':
            $end = $strict ? '$' : '';
            return (bool) preg_match( "/^{$token}:[0-9.E+-]+;$end/", $data );
    }
    return false;