简体   繁体   English

PHP如何迭代hierarhical平面阵列?

[英]PHP how to iterate over hierarhical flat array?

I have this data set, which is a flat hierarhical multi-dimensional array: 我有这个数据集,这是一个平面的多维数组:

[
    [
        'title' => 'Skylake',
        'type' => 'category',
        'items' => 
        [
            [
                'title' => 'Core i3',
                'type' => 'category',
                'items' => 
                [
                    [
                        'title' => '6100',
                        'type' => 'product',
                        'price' => 100.0,
                    ],
                    [
                        'title' => '6300',
                        'type' => 'product',
                        'price' => 110.0,
                    ],
                ],
            ],
            [
                'title' => 'Core i7',
                'type' => 'category',
                'items' => [
                    [
                        'title' => '7700',
                        'type' => 'product',
                        'price' => 330.0,
                    ],
                    [
                        'title' => '7700K',
                        'type' => 'product',
                        'price' => 370.0,
                    ],
                ],
            ],
        ],
    ],
    [
        'title' => 'KabyLake',
        'type' => 'category',
    ]
];

As you can see there are two main category: Skylake and Kabylake, and these contains other subcategories and subcategories contain products. 正如您所看到的,有两个主要类别:Skylake和Kabylake,其中包含其他子类别和子类别包含的产品。

I have tried to iterate over this flat array, but something went wrong, because the 'core i7' category will not know that its parent is 'Skylake'. 我试图迭代这个平面阵列,但出了点问题,因为'核心i7'类别不会知道它的父级是'Skylake'。 When I insert the data into the database its parent_id will be null. 当我将数据插入数据库时​​,其parent_id将为null。

   /**
     * Creates catalog.
     * @param mixin $sampleItems sample items
     * @param interger $categoryId id of category (parent id)
     */
    private function createCatalog(&$sampleItems, $categoryId = null)
    {
        foreach ($sampleItems as $sampleItem) {
            if ($sampleItem['type'] == 'category') {
                $categoryId = $this->createCategory($sampleItem, $categoryId);
            } else {
                $this->createProduct($sampleItem, $categoryId);
            }
            $hasItems = isset($sampleItem['items']) && is_array($sampleItem['items']);
            if ($hasItems) {
                $this->createCatalog($sampleItem['items'], $categoryId);
                $categoryId = null;
            }
        }
    }

    /**
     * Create category.
     * @param mixin $sampleData
     * @param integer $parentId ID of parent category
     * @return integer ID of created category
     */
    private function createCategory($sampleData, $parentId)
    {
        $category = new Category();
        if ($parentId !== null) {
            $category->parent_id = $parentId;
        }
        $category->title = $sampleData['title'];
        $category->status = 1;
        $category->save();

        return $category->id;
    }

    /**
     * Create Product.
     * @param mixin $sampleData
     * @param integer $categoryId
     */
    private function createProduct($sampleData, $categoryId)
    {
        $product = new Product();
        if ($categoryId !== null) {
            $product->category_id = $categoryId;
        }
        $product->title = $sampleData['title'];
        $product->price = $sampleData['price'];
        $product->description = $sampleData['description'];
        $product->status = 1;
        $product->save();
    }

Unfortunately this is the current hierarchy in the database: 不幸的是,这是数据库中的当前层次结构:

Skylake
  Core i3
Core i7
KabyLake

The Core i7 should be under the Skylake. Core i7应该属于Skylake。

I think the problem is that $parentId will null for Core i7. 我认为问题是$ parentId将为Core i7归零。

But I do not see why. 但我不明白为什么。

The problem is that you're using the same variable $categoryId for the parent of the current category and for the parents of the sub-categories that you're creating in the loop. 问题是您对当前类别的父级以及您在循环中创建的子$categoryId的父级使用相同的变量$categoryId When you do $categoryId = null; 当你做$categoryId = null; after creating a nested catalog, that affects the next call to createCategory() . 创建嵌套目录后,会影响对createCategory()的下一次调用。

Use a different variable, I use $subcat below. 使用不同的变量,我使用下面的$subcat

private function createCatalog(&$sampleItems, $categoryId = null)
{
    $subcat = null;
    foreach ($sampleItems as $sampleItem) {
        if ($sampleItem['type'] == 'category') {
            $subcat = $this->createCategory($sampleItem, $categoryId);
        } else {
            $this->createProduct($sampleItem, $categoryId);
        }
        $hasItems = isset($sampleItem['items']) && is_array($sampleItem['items']);
        if ($hasItems) {
            $this->createCatalog($sampleItem['items'], $subcat);
            $subcat = null;
        }
    }
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM