You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

PHP多维数组条件清理优化:替代嵌套foreach的高效方案

问题

我开发了一个程序,把JSON转换为PHP数组后,通过嵌套foreach循环遍历多维数组,删除值为0、空字符串、null或**"Api "**的键值对,最后再转回JSON。但嵌套循环代码冗余,没法适配层级更多的多维数组,想找更简洁的实现方案。

示例JSON

{
    "UniqueId": "PO3589472",
    "FareType": 2,
    "BookedBy": "Api ",
    "OrderBy": "Api ",
    "ClientBalance": 0,
    "Error": null,
    "Success": true,
    "TktTimeLimit": "2022-08-10T14:11:45",
    "Category": 21,
    "Status": 21,
    "RefundMethod": 1,
    "TravelItinerary": {
        "ItineraryInfo": {
            "ItineraryPricing": {
                "BaseFare": 8469250,
                "ServiceTax": 0,
                "TotalTax": 993000,
                "TotalFare": 9462250,
                "TotalCommission": 0,
                "Currency": "IRR"
            },
            "CustomerInfoes": [
                {
                    "Customer": {
                        "Gender": 0,
                        "PassengerType": 1,
                        "PassportNumber": "",
                        "NationalId": "1829961233",
                        "Nationality": "IR",
                        "DateOfBirth": "1996-07-08T00:00:00",
                        "PassportExpireDate": "0001-01-01T00:00:00",
                        "PassportIssueCountry": "IR",
                        "PassportIssueDate": "2022-08-10T00:00:00",
                        "PaxName": {
                            "PassengerFirstName": "MAJID",
                            "PassengerMiddleName": null,
                            "PassengerLastName": "MAJIDIFAR",
                            "PassengerTitle": 0
                        }
                    },
                    "ETickets": "8151405444745",
                    "ETicketNumbers": [
                        {
                            "ETicketNumber": "8151405444745",
                            "EticketStatus": 1,
                            "IsRefunded": false,
                            "DateOfIssue": "2022-08-10T13:58:47",
                            "AirlinePnr": "TXNXM",
                            "TotalRefund": 0
                        }
                    ]
                }
            ],
            "ReservationItems": [
                {
                    "AirEquipmentType": "737",
                    "AirlinePnr": "TXNXM",
                    "ArrivalAirportLocationCode": "ABD",
                    "ArrivalDateTime": "2022-08-17T23:25:00",
                    "ArrivalTerminal": "",
                    "Baggage": "20KG",
                    "DepartureAirportLocationCode": "THR",
                    "DepartureDateTime": "2022-08-17T22:05:00",
                    "DepartureTerminal": "Terminal 4",
                    "FlightNumber": "3750",
                    "JourneyDuration": "01:20",
                    "JourneyDurationPerMinute": 0,
                    "MarketingAirlineCode": "EP",
                    "OperatingAirlineCode": "EP",
                    "ResBookDesigCode": "Y",
                    "StopQuantity": 0,
                    "IsCharter": false,
                    "TechnicalStops": [],
                    "IsReturn": false,
                    "CabinClassCode": 1
                }
            ],
            "TripDetailPtcFareBreakdowns": [
                {
                    "PassengerTypeQuantity": {
                        "PassengerType": 1,
                        "Quantity": 1
                    },
                    "TripDetailPassengerFare": {
                        "BaseFare": 8469250,
                        "ServiceTax": 0,
                        "Tax": 993000,
                        "TotalFare": 9462250,
                        "Commission": 0,
                        "Currency": "IRR"
                    }
                }
            ],
            "PhoneNumber": "09359276735",
            "Email": "info@iran-tech.com",
            "ItineraryFareFamily": null
        },
        "BookingNotes": [],
        "Services": []
    },
    "ValidatingAirlineCode": "EP",
    "DirectionInd": 1,
    "OnlineCheckIn": false,
    "AirRemark": [],
    "curl_error": false
}

当前嵌套foreach代码

<?php
    $jsondata = file_get_contents("test_php.json");
    $json = json_decode($jsondata, true);
    

    foreach($json as $keys1 => $values1){
        if($values1 == 0 || $values1 == "" || $values1 == "Api " || !isset($values1) ){
            unset($json[$keys1]);
        }else{
            if(is_array($values1)){
                foreach($values1 as $keys2 => $values2){
                    if($values2 == 0 || $values2 == "" || $values2 == "Api " || !isset($values2) ){
                        unset($json[$keys1][$keys2]);
                    }else{
                        if(is_array($values2)){
                            foreach($values2 as $keys3 => $values3){
                                if($values3 == 0 || $values3 == "" || $values3 == "Api " || !isset($values3) ){
                                    unset($json[$keys1][$keys2][$keys3]);
                                }else{
                                    if(is_array($values3)){
                                        foreach($values3 as $keys4 => $values4){
                                            if($values4 == 0 || $values4 == "" || $values4 == "Api " || !isset($values4) ){
                                                unset($json[$keys1][$keys2][$keys3][$keys4]);
                                            }else{
                                                if(is_array($values4)){
                                                    foreach($values4 as $keys5 => $values5){
                                                        if($values5 == 0 || $values5 == "" || $values5 == "Api " || !isset($values5) ){
                                                            unset($json[$keys1][$keys2][$keys3][$keys4][$keys5]);
                                                        }else{
                                                            if(is_array($values5)){
                                                                foreach($values5 as $keys6 => $values6){
                                                                    if($values6 == 0 || $values6 == "" || $values6 == "Api " || !isset($values6) ){
                                                                        unset($json[$keys1][$keys2][$keys3][$keys4][$keys5][$keys6]);
                                                                    }else{
                                                                        if(is_array($values6)){
                                                                            foreach($values6 as $keys7 => $values7){
                                                                                if($values7 == 0 || $values7 == "" || $values7 == "Api " || !isset($values7) ){
                                                                                    unset($json[$keys1][$keys2][$keys3][$keys4][$keys5][$keys6][$keys7]);
                                                                                }
                                                                            }
                                                                        }
                                                                    }
                                                                }
                                                            }
                                                        }
                                                    }
                                                }
                                            }
                                        }
                                    }
                                }
                            }
                        }

                    }
                }
            }
        }
    }
    $path = "test_php(final).json";
    $converter = json_encode($json, JSON_PRETTY_PRINT);
    $open = fopen($path, 'w');
    fwrite($open, $converter);
    fclose($open);
?>
解决方案

用递归函数就能彻底解决嵌套循环的冗余问题,递归可以自动遍历任意层级的多维数组,不需要手动写多层foreach。核心思路是:遍历数组的每个元素,判断是否需要保留;如果元素是数组,就递归处理这个子数组,再判断处理后的子数组是否需要保留(比如空数组是否要移除,可按需调整)。

实现代码

<?php
// 定义递归过滤函数
function filterArray($array) {
    foreach ($array as $key => $value) {
        // 判断当前值是否需要移除
        if ($value === 0 || $value === "" || $value === "Api " || $value === null) {
            unset($array[$key]);
        } elseif (is_array($value)) {
            // 递归处理子数组
            $array[$key] = filterArray($value);
            // 可选:如果处理后的子数组为空,也移除该键(按需开启)
            // if (empty($array[$key])) {
            //     unset($array[$key]);
            // }
        }
    }
    return $array;
}

// 读取JSON文件并转换为数组
$jsondata = file_get_contents("test_php.json");
$jsonArray = json_decode($jsondata, true);

// 执行过滤
$filteredArray = filterArray($jsonArray);

// 转换回JSON并保存
$path = "test_php(final).json";
$converter = json_encode($filteredArray, JSON_PRETTY_PRINT);
file_put_contents($path, $converter);
?>

代码说明

  1. 递归函数filterArray:
    • 遍历数组的每个键值对,先判断值是否属于要删除的范围(0、空字符串、"Api "、null),是则直接移除。
    • 如果值是数组,就递归调用自身处理这个子数组,处理后替换原数组中的子数组。
    • 可选:如果处理后的子数组为空(比如原数据中的BookingNotes),可以选择移除这个键,只需要取消注释对应的判断代码即可。
  2. 简化IO操作:用file_put_contents替代fopen/fwrite/fclose,代码更简洁。
  3. 兼容性:不管数组有多少层级,递归函数都能自动处理,完全解决嵌套foreach的冗余问题。

内容的提问来源于stack exchange,提问作者mahmoudkhani

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 20:35:20