Php 递归函数中的意外行为

Php 递归函数中的意外行为,php,arrays,recursion,Php,Arrays,Recursion,该任务是递归地删除带有其键的error=>4(即带有该值的键)的数组,然后将保留的数组转换为对象。 传入阵列的结构可能不同。这方面有两个例子: // Example input #1 $ex_input_1 = array( 'files' => array( 0 => array( 'name' => 'file.jpg', 'size' => '244235', 'tmp_

该任务是递归地删除带有其键的error=>4(即带有该值的键)的数组,然后将保留的数组转换为对象。 传入阵列的结构可能不同。这方面有两个例子:

// Example input #1
$ex_input_1 = array(
    'files' => array(
        0 => array(
            'name' => 'file.jpg',
            'size' => '244235',
            'tmp_name' => '/usr/tmp/24ffds.tmp',
            'error' => 0
        ),

        1 => array(
            'name' => '',
            'size' => '',
            'tmp_name' => '',
            'error' => 4
        )
    ),

    'cover' => array(
        'name' => '',
        'size' => '',
        'tmp_name' => '',
        'error' => 4
    ),

    'document' => array(
        'name' => 'file.doc',
        'size' => '244235',
        'tmp_name' => '/usr/tmp/24ffds.tmp',
        'error' => 0
    )
);

// Example input #2
$ex_input_2 = array(
    0 => array(
        'name' => 'file.jpg',
        'size' => '244235',
        'tmp_name' => '/usr/tmp/24ffds.tmp',
        'error' => 0
    ),

    1 => array(
        'name' => '',
        'size' => '',
        'tmp_name' => '',
        'error' => 4
    )
);
i、 e具有
名称、大小、tmp\u名称、错误
键的数组可能处于任何级别

我尝试的是: 尝试用两个方法编写一个简单的处理程序,其中第一个是递归处理程序,第二个是递归方法。以下是它的相关部分:

<?php

class FileInputParser
{
    /**
     * Recursively hydrate array entires skipping empty files
     * 
     * @param array $files
     * @return array
     */
    public function hydrateAll(array $files)
    {
        foreach ($files as $name => $file) {
            if (!is_array($file)) {
                continue;
            }

            foreach ($file as $key => $value) {
                if (is_array($value)) {
                    // Recursise call
                    $files[$name] = $this->hydrateAll($files[$name]);
                } else {
                    $target = $this->hydrateSingle($file);

                    // Here I'm EXPLICTLY asking not to push an array, which has error = 4
                    // But it pushes anyway!!
                    if ($target !== false) {
                        unset($files[$name]);
                    }
                }
            }
        }

        return $files;
    }

    /**
     * Hydrates a single file item
     * 
     * @param array $file
     * @return mixed
     */
    private function hydrateSingle(array $file)
    {
        $entity = new stdclass;
        $entity->name = $file['name'];
        $entity->tmp_name = $file['tmp_name'];
        $entity->error = $file['error'];
        $entity->size = $file['size'];

        if ($entity->error != 4) {
            return $entity;
        } else {
            // Returning false to indicate, that this one should not be pushed in output
            return false;
        }
    }
}

这里有一个递归函数,可以执行您想要的过滤。当它到达树的底部时,它检查
error==4
,如果是,则返回空数组,否则返回当前数组。在下一级,所有返回的空值都将由
数组\u过滤器删除:

Array ( 
    [files] => Array (
        [0] => Array ( 
            [name] => file.jpg
            [size] => 244235
            [tmp_name] => /usr/tmp/24ffds.tmp
            [error] => 0
        )
    )
    [document] => Array (
         [name] => file.doc
         [size] => 244235
         [tmp_name] => /usr/tmp/24ffds.tmp
         [error] => 0
    ) 
)

Array ( 
    [0] => Array (
        [name] => file.jpg
        [size] => 244235
        [tmp_name] => /usr/tmp/24ffds.tmp
        [error] => 0
    )
)
过滤两个输入数组的输出:

function array_filter_recursive($array) {
    if (isset($array['error'])) {
        // bottom of tree
        return $array['error'] == 4 ? array() : $array;
    }
    foreach ($array as $key => $value) {
        $array[$key] = array_filter_recursive($value);
    }
    // remove any empty values
    return array_filter($array);
}
Array ( 
    [files] => Array (
        [0] => Array ( 
            [name] => file.jpg
            [size] => 244235
            [tmp_name] => /usr/tmp/24ffds.tmp
            [error] => 0
        )
    )
    [document] => Array (
         [name] => file.doc
         [size] => 244235
         [tmp_name] => /usr/tmp/24ffds.tmp
         [error] => 0
    ) 
)

Array ( 
    [0] => Array (
        [name] => file.jpg
        [size] => 244235
        [tmp_name] => /usr/tmp/24ffds.tmp
        [error] => 0
    )
)