-->

如何反序列化的Perl数据::在PHP自卸车输出(How to deserialize Perl D

2019-09-22 07:21发布

我有一个这样的字符串在Perl出口变量的结果:

$VAR1 = {
    'guard' => undef,
    'work_hand' => undef,
    'images' => 
        {'1' => 
            {
            'mini_height' => 150,
            'width' => 150,
            'extension' => 'jpg',
            'filename' => 'object_1.1330907414.96873.jpg',
            'mini_width' => 150,
            'class' => 'Ontico::Image',
            'height' => 150,
            'mini_filename' => 'object_1.1330907414.96873.mini.jpg',
            'size' => 26053,
            'symname' => 'big_logo'
            },
        '2' => 
            {
            'width' => 48,
            'extension' => 'jpg',
            'alt' => 'Даниэле Галлоппа',
            'height' => 48,
            'mini_filename' => 'object_91.1235312905.mini.jpg',
            'size' => 12809,
            'symname' => 'logo',
            'mini_height' => 150,
            'filename' => 'object_91.1235312905.jpg',
            'mini_width' => 150,
            'class' => 'Ontico::Image'
            }
        },
        'show_league_banner' => 0,
        'back_hand' => undef,
        'weight_category' => undef,
        'stick_position' => undef
    };

我怎样才能反序列化PHP这些数据?

PS我已经在这个格式DB数据,我不能将其更改为JSON或其他。

Answer 1:

既然你说你不能改变格式:

我不喜欢使用eval,而是因为你的语法是如此接近预期的PHP数组的语法,我想我们可以让它滑动。

设置$string等于从你的数据库适合以下格式的内容。 使用您提供的数据,请参见下面的工作示例。 在一天结束时,PHP将在你的Perl变种的开始新的解析的阵列设置变量。

由于它是将是一个文本块/大串,这样做:

<?php
$string = "\$VAR1 = {
    'guard' => undef,
    'work_hand' => undef,
    'images' =>
        {'1' =>
            {
            'mini_height' => 150,
            ... // truncated for readability
    };";

$res = str_replace(array("{", "}", 'undef'), array("array(", ")", "''"), $string);

eval($res);

print_r($VAR1);

你的结果是:

Array
(
    [guard] =>
    [work_hand] =>
    [images] => Array
        (
            [1] => Array
                (
                    [mini_height] => 150 ...

注:我建议你花时间,现在改造和数据库内容升级到更标准格式简单的事实,它会更容易在未来的维护。

您可以通过数据库循环,抓住所有的内容一行一行,在这一点上,你运行数据成以上的功能,并敷在json_encode()和更新与新的JSON字符串你的数据库行。 这将节省您在未来的头痛,让你更新了新标准的所有数据。



Answer 2:

你有一些建议,试图解析它这种或那种方式,但真正的问题是,为什么?

为什么不只是加载它,并吐出了一个等效的JSON字符串一个小Perl程序。

然后,您既可以调用Perl程序从PHP中做转换; 这将意味着你正在使用Perl阅读Perl的格式,这将保证正确的转换。

在批处理或(更好的)运行对整个数据库,以摆脱来自DB Perl的具体数据格式; 那么你可以使用PHP的标准JSON功能。

那么这将使生活变得更简单,在你的PHP代码(或任何其他语言,你需要在日后读取数据)。



Answer 3:

因为它不是JSON,但它看起来像JSON,你可以尝试修改JSON库与该格式的工作。 我把这个JSON库 ,替代:=>和加入undef ,你可以看到这里 (线496,671和681)。 这是很简单的,真的,我想你可以解决类似的方式等方面的差异。

结果是:

stdClass Object
(
    [guard] => 
    [work_hand] => 
    [images] => stdClass Object
        (
            [1] => stdClass Object
                (
                    [mini_height] => 150
                    [width] => 150
                    [extension] => jpg
                    [filename] => object_1.1330907414.96873.jpg
                    [mini_width] => 150
                    [class] => Ontico::Image
                    [height] => 150
                    [mini_filename] => object_1.1330907414.96873.mini.jpg
                    [size] => 26053
                    [symname] => big_logo
                )

            [2] => stdClass Object
                (
                    [width] => 48
                    [extension] => jpg
                    [alt] => Даниэле Галлоппа
                    [height] => 48
                    [mini_filename] => object_91.1235312905.mini.jpg
                    [size] => 12809
                    [symname] => logo
                    [mini_height] => 150
                    [filename] => object_91.1235312905.jpg
                    [mini_width] => 150
                    [class] => Ontico::Image
                )

        )

    [show_league_banner] => 0
    [back_hand] => 
    [weight_category] => 
    [stick_position] => 
)

这是你在找什么?



Answer 4:

明显的和唯一的可靠的解决方案是使用Perl反序列化和重新序列化输入到一个标准的格式。 Perl程序可以完成这个任务并不需要非常大的,无论是。

// receive input in Perl's Data::Dumper format and produce PHP object output
function perl_dd_to_php( $dd_output ) {
    $process = proc_open( "perl -000 -MJSON -e 'print encode_json eval <>'",
                          array( array("pipe","r"), array("pipe","w") ),
                          $pipes );
    fwrite($pipes[0], $dd_output );
    fclose($pipes[0]);

    $json_string = stream_get_contents($pipes[1]);
    fclose($pipes[1]);

    return json_decode($json_string);
}


Answer 5:

use JSON;

(或任何其他数据交换格式如XML)

JSON文档和例子可在CPAN



Answer 6:

如果你可以改变Perl代码,然后做的阿蒙建议 ,并使用像一些标准的序列化格式, JSON或XML或YAML ,你可以在PHP反序列化。

你甚至可以用Perl输出PHP的本机序列化格式 ,如果你真的想,虽然我通常不会建议。 (约当你下次要反序列化,比方说,Python的相同的数据是什么?)

如果你不能改变Perl代码,你只好硬着头皮尝试分析数据::自卸车输出PHP。 我找不到任何现有的代码来做到这一点,所以它看起来像您可能需要自己编写。 这可能是一份工作解析器生成器 ,虽然格式(通常)很简单,你也许可以只手代码它。


编辑:既然你说你在数据库中有这样的序列化的数据,为什么不只是写一个Perl程序来读取数据,并将其转换成JSON一样更标准的序列化格式?



文章来源: How to deserialize Perl Data::Dumper output in PHP