如何从print_r打印的数组的输出创建一个数组?

时间:2011-08-11 12:34:10

标签: php arrays string variables type-conversion

我有一个数组:

$a = array('foo' => 'fooMe');

我做了:

print_r($a);

打印:

Array ( [foo] => printme )

是否有功能,所以在执行时:

needed_function('    Array ( [foo] => printme )');

我会回到数组array('foo' => 'fooMe');吗?

11 个答案:

答案 0 :(得分:26)

我实际上编写了一个将“stringed array”解析为实际数组的函数。显然,它有点hacky等等,但它适用于我的测试用例。这是http://codepad.org/idlXdij3上正常运行原型的链接。

对于那些不想点击链接的人,我也会内联发布代码:

<?php
     /**
      * @author ninetwozero
      */
?>
<?php
    //The array we begin with
    $start_array = array('foo' => 'bar', 'bar' => 'foo', 'foobar' => 'barfoo');

    //Convert the array to a string
    $array_string = print_r($start_array, true);

    //Get the new array
    $end_array = text_to_array($array_string);

    //Output the array!
    print_r($end_array);

    function text_to_array($str) {

        //Initialize arrays
        $keys = array();
        $values = array();
        $output = array();

        //Is it an array?
        if( substr($str, 0, 5) == 'Array' ) {

            //Let's parse it (hopefully it won't clash)
            $array_contents = substr($str, 7, -2);
            $array_contents = str_replace(array('[', ']', '=>'), array('#!#', '#?#', ''), $array_contents);
            $array_fields = explode("#!#", $array_contents);

            //For each array-field, we need to explode on the delimiters I've set and make it look funny.
            for($i = 0; $i < count($array_fields); $i++ ) {

                //First run is glitched, so let's pass on that one.
                if( $i != 0 ) {

                    $bits = explode('#?#', $array_fields[$i]);
                    if( $bits[0] != '' ) $output[$bits[0]] = $bits[1];

                }
            }

            //Return the output.
            return $output;

        } else {

            //Duh, not an array.
            echo 'The given parameter is not an array.';
            return null;
        }

    }
?>

答案 1 :(得分:14)

如果您想将数组存储为字符串,请使用serialize [docs]unserialize [docs]

回答你的问题:不,没有内置函数可以将print_r的输出再次解析为数组。

答案 2 :(得分:8)

对于带有子阵列的数组输出,ninetwozero提供的解决方案不起作用,您可以尝试使用适用于复杂数组的此函数:

<?php

$array_string = "

Array
 (
   [0] => Array
    (
       [0] => STATIONONE
       [1] => 02/22/15 04:00:00 PM
       [2] => SW
       [3] => Array
            (
                [0] => 4.51
            )

        [4] => MPH
        [5] => Array
            (
                [0] => 16.1
            )

        [6] => MPH
    )

     [1] => Array
    (
        [0] => STATIONONE
        [1] => 02/22/15 05:00:00 PM
        [2] => S
        [3] => Array
            (
                [0] => 2.7
            )

        [4] => MPH
        [5] => Array
            (
                [0] => 9.61
            )

        [6] => MPH
    )
)
";

print_r(print_r_reverse(trim($array_string)));

function print_r_reverse(&$output)
{
    $expecting = 0; // 0=nothing in particular, 1=array open paren '(', 2=array element or close paren ')'
    $lines = explode("\n", $output);
    $result = null;
    $topArray = null;
    $arrayStack = array();
    $matches = null;
    while (!empty($lines) && $result === null)
    {
        $line = array_shift($lines);
        $trim = trim($line);
        if ($trim == 'Array')
        {
            if ($expecting == 0)
            {
                $topArray = array();
                $expecting = 1;
            }
            else
            {
                trigger_error("Unknown array.");
            }
        }
        else if ($expecting == 1 && $trim == '(')
        {
            $expecting = 2;
        }
        else if ($expecting == 2 && preg_match('/^\[(.+?)\] \=\> (.+)$/', $trim, $matches)) // array element
        {
            list ($fullMatch, $key, $element) = $matches;
            if (trim($element) == 'Array')
            {
                $topArray[$key] = array();
                $newTopArray =& $topArray[$key];
                $arrayStack[] =& $topArray;
                $topArray =& $newTopArray;
                $expecting = 1;
            }
            else
            {
                $topArray[$key] = $element;
            }
        }
        else if ($expecting == 2 && $trim == ')') // end current array
        {
            if (empty($arrayStack))
            {
                $result = $topArray;
            }
            else // pop into parent array
            {
                // safe array pop
                $keys = array_keys($arrayStack);
                $lastKey = array_pop($keys);
                $temp =& $arrayStack[$lastKey];
                unset($arrayStack[$lastKey]);
                $topArray =& $temp;
            }
        }
        // Added this to allow for multi line strings.
    else if (!empty($trim) && $expecting == 2)
    {
        // Expecting close parent or element, but got just a string
        $topArray[$key] .= "\n".$line;
    }
        else if (!empty($trim))
        {
            $result = $line;
        }
    }

    $output = implode("\n", $lines);
    return $result;
}

/**
* @param string $output : The output of a multiple print_r calls, separated by newlines
* @return mixed[] : parseable elements of $output
*/
function print_r_reverse_multiple($output)
{
    $result = array();
    while (($reverse = print_r_reverse($output)) !== NULL)
    {
        $result[] = $reverse;
    }
    return $result;
}

?>

有一个小错误,如果你有一个空值(空字符串),它会嵌入到之前的值中。

答案 3 :(得分:7)

没有。但您可以同时使用serializejson_*函数。

$a = array('foo' => 'fooMe');
echo serialize($a);

$a = unserialize($input);

或者:

echo json_encode($a);

$a = json_decode($input, true);

答案 4 :(得分:5)

你不能用print_r
来做到这一点 var_export应该允许类似的内容,但不完全是你要求的内容

http://php.net/manual/en/function.var-export.php

$val = var_export($a, true);
print_r($val);
eval('$func_val='.$val.';');

答案 5 :(得分:2)

有一个很好的在线工具,它的名字很简单:

print_r to json online converter

从JSON对象到创建具有json_decode函数的数组不远:

要从中获取数组,请将第二个参数设置为true。如果你没有,你会得到一个对象。

json_decode($jsondata, true);

答案 6 :(得分:2)

我认为我的功能也很酷,可用于嵌套数组:

function print_r_reverse($input)
{
    $output = str_replace(['[', ']'], ["'", "'"], $input);
    $output = preg_replace('/=> (?!Array)(.*)$/m', "=> '$1',", $output);
    $output = preg_replace('/^\s+\)$/m', "),\n", $output);
    $output = rtrim($output, "\n,");
    return eval("return $output;");
}

NB:最好不要将其与用户输入数据一起使用

答案 7 :(得分:1)

使用

var_export(array('Sample array', array('Apple', 'Orange')));

输出:

array (
  0 => 'Sample array',
  1 => 
  array (
    0 => 'Apple',
    1 => 'Orange',
  ),
)

答案 8 :(得分:0)

快速功能(无需检查是否发送了良好的数据):

function textToArray($str)
{
    $output = [];

    foreach (explode("\n", $str) as $line) {

        if (trim($line) == "Array" or trim($line) == "(" or trim($line) == ")") {
            continue;
        }

        preg_match("/\[(.*)\]\ \=\>\ (.*)$/i", $line, $match);

        $output[$match[1]] = $match[2];
    }

    return $output;
}

这是预期的输入:

Array
(
    [test] => 6
)

答案 9 :(得分:0)

json_encode()json_decode()函数可以做到。

$asso_arr = Array([779] => 79 => [780] => 80 [782] => 82 [783] => 83);
$to_string = json_encode($asso_arr);

它将为json格式{"779":"79","780":"80","782":"82","783":"83"}

然后我们将其转换为json_decode(),然后给出与原始数组相同的关联数组:

print_r(json_decode($to_string));

输出将为Array([779] => 79 => [780] => 80 [782] => 82 [783] => 83)的关联数组格式。

答案 10 :(得分:0)

我是这样解释问题的:

function parsePrintedArray($s){
    $lines = explode("\n",$s);
    $a = array();
    foreach ($lines as $line){
        if (strpos($line,"=>") === false)
            continue;
        $parts = explode('=>',$line);
        $a[trim($parts[0],'[] ')] = trim($parts[1]);
    }
    return $a;
}

适用于对象和数组:

$foo = array (
    'foo' => 'bar',
    'cat' => 'dog'
);

$s = print_r($foo,1);
$a = parsePrintedArray($s);
print_r($a);

输出:

Array
(
    [foo] => bar
    [cat] => dog
) 

不适用于嵌套数组,但简单快速。