簡體   English   中英

PHP遞歸JSON子級搜索

[英]PHP Recursive JSON Children Search

我需要解析如下所示的JSON:

{
    "mdfId":"282088127",
    "mdfConcept":"ME 3400EG-12CS-M Switch",
    "children":[
        {
            "mdfId":"007",
            "mdfConcept":"Another item",
            "children": [
                // many more here
            ]
        },
        {
             "mdfId":"008",
             "mdfConcept":"Another one",
             "children": [
                 {
                     "mdfId":"010",
                     "mdfConcept":"What I'm looking for!",
                     "children": [] // no children
                 }
             ]
        },
        // many more here
    ]
},

這是一種遞歸結構,其中每個元素都具有mdfIdmdfConceptchildren項鍵。

假設我需要在此結構中找到ID=010節點。 我不知道它位於哪一級(例如,它可以在頂層,也可以在下面幾個children節點)。

我當前的方法是:

$mdfId = '010'; // what I'm loking for

foreach ($jsonResponse as $category) {
    while (true) {
        if ($category['mdfId'] == $mdfId) {
            // we found it!
            $categoryDevices[$mdfId] = $category['children'];
            break 2;
        }

        if (!empty($category['children'])) {
            next_cat:

            if (is_null($category['children'])) {
                break;
            }

            $category = array_shift($category['children']);
            continue;
        }

        if (empty($category['children'])) {
            goto next_cat;
        }
    }
}

但是目前的方法遺漏了一些情況。 如何優化此遞歸循環,以便它檢查同一級別上的所有節點,並通過任意數量的children項鍵檢查每個節點?

JSON對象的一個​​令人尷尬的特征是,盡管每個children成員都是“子”結構的數組, 但最頂層的對象是對象本身 ,因此這是真正遞歸方法的障礙。

我們可以通過將源JSON對象轉換為與嵌套級別相同的結構來解決,即:

  • $jsonResponse作為原始對象
  • 使用['children' => $jsonResponse]代替

這樣,它應該可以像這樣工作:

$mdfId = '010'; // what I'm loking for

if ($result = look4id(['children' => $jsonResponse], $mdfId) {
    $categoryDevices[$mdfId] = $result;
}

function look4id($source, $id) {
    foreach ($source as $child) {
        if ($child['mdfId'] == $id) {
            return $source['children'];
        } else {
            if ($source['children']) {
                return look4id($source['children'], $id);
            }
        }
    }
}

因此,基本上,我編寫了一個不返回任何內容,而是從參數中填充變量的函數。

function findRecursiveArrayNodeById($id, $array, &$node) {
    foreach ($array as $child) {
        if (isset($child['mdfId']) && $child['mdfId'] == $id) {
            $node = $child;
            return;
        }

        if (!empty($child['children'])) {
            findRecursiveArrayNodeById($id, $child['children'], $node);
        }
    }
}

用法如下:

$result = false;

findRecursiveArrayNodeById($mdfId, $category_json, $result);

if (!$result) {
    println("did not find {$mdfId}");
    continue;
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM