Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/php/292.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 将树转换为平面阵列_Php - Fatal编程技术网

Php 将树转换为平面阵列

Php 将树转换为平面阵列,php,Php,我无法将树结构转换为平面结构。我的树结构如下所示: [ { "id": "X", "label": "X", "data": { "23": 1, "26": 2, "20": 38944000 }, "children": [ { "id": "Y", "label": "Y", "data": { "23": 303000,

我无法将树结构转换为平面结构。我的树结构如下所示:

[
  {
    "id": "X",
    "label": "X",
    "data": {
      "23": 1,
      "26": 2,
      "20": 38944000
    },
    "children": [
      {
        "id": "Y",
        "label": "Y",
        "data": {
          "23": 303000,
          "26": 704000,
          "20": 2486000
        },
        "children": [
          {
            "id": "Z",
            "label": "Z",
            "data": {
              "23": 0,
              "26": 0,
              "20": 2486000
            },
            "children": [],
            "level": 2,
            "type": "category"
          },
          {
            "id": "A",
            "label": "A",
            "data": {
              "23": 303000,
              "26": 704000,
              "20": 0
            },
            "children": [],
            "level": 2,
            "type": "category"
          }
        ],
        "level": 1,
        "type": "company"
      },
      {
        "id": "B",
        "label": "B",
        "data": {
          "23": 9627000,
          "26": 9580000,
          "20": 9428000
        },
        "children": [
          {
            "id": "C",
            "label": "C",
            "data": {
              "23": 6021000,
              "26": 6030000,
              "20": 9428000
            },
            "children": [],
            "level": 2,
            "type": "category"
          },
          {
            "id": "D",
            "label": "D",
            "data": {
              "23": 2205000,
              "26": 1932000,
              "20": 0
            },
            "children": [],
            "level": 2,
            "type": "category"
          },
          {
            "id": "E",
            "label": "E",
            "data": {
              "23": 737000,
              "26": 874000,
              "20": 0
            },
            "children": [],
            "level": 2,
            "type": "category"
          },
          {
            "id": "F",
            "label": "F",
            "data": {
              "23": 664000,
              "26": 744000,
              "20": 0
            },
            "children": [],
            "level": 2,
            "type": "category"
          }
        ],
        "level": 1,
        "type": "company"
      }
    ],
    "level": 0,
    "type": "client"
  }
]
我想把它变成一个结构:

[
  {
    "client": "X",
    "company": "Y",
    "category": "Z",
    "23": 0,
    "26": 0,
    "20": 2486000
  },
  {
    "client": "X",
    "company": "Y",
    "category": "A",
    "23": 303000,
    "26": 704000,
    "20": 0
  },
  {
    "client": "X",
    "company": "B",
    "category": "C",
    "23": 6021000,
    "26": 6030000,
    "20": 9428000
  },
  {
    "client": "X",
    "company": "B",
    "category": "D",
    "23": 2205000,
    "26": 1932000,
    "20": 0
  },
  {
    "client": "X",
    "company": "B",
    "category": "E",
    "23": 664000,
    "26": 744000,
    "20": 0
  },
  {
    "client": "X",
    "company": "B",
    "category": "F",
    "23": 664000,
    "26": 744000,
    "20": 0
  }
]
我试着这样做:

/**
     * Prepare flat data array.
     *
     * @param CompareForecastsReportDto $report
     * @param GetCompareForecastsReportQuery $query
     */
    private function prepareFlatTable(
        CompareForecastsReportDto $report,
        GetCompareForecastsReportQuery $query
    ): void
    {
        $this->prepareHeaderColumns($report, $query);
        $flatData = [];

        foreach ($report->getData() as $dataRow) {
            $data = $this->flatten($dataRow);

            $flatData[] = $data;
        }
var_dump($flatData);exit;
        $this->setFlatData($flatData);
    }

    /**
     * To flat array.
     *
     * @param CompareReportRowDto $compareReportRowDto
     *
     * @return CompareReportRowDto[]
     */
    private function flatten(
        CompareReportRowDto $compareReportRowDto
    ): array {
        $result = [];

        $result = array_merge($result, [$compareReportRowDto->getType() => $compareReportRowDto->getLabel()]);
        foreach($compareReportRowDto->getChildren() as $item) {
            if (count($item->getChildren())) {
                $result = array_merge($result, $this->flatten($item));
            }

            $result = array_merge($result, [$item->getType() => $item->getLabel()]);
            $result = array_merge($result, $item->getData());
但结果并不正确

使用递归是很重要的

通过使用trincot的答案,我的函数最终如下所示:

/**
     * To flat array.
     *
     * @param CompareReportRowDto $compareReportRowDto
     *
     * @return array
     */
    private function flatten(
        CompareReportRowDto $compareReportRowDto
    ): array {
        $result = [];

        foreach($compareReportRowDto->getChildren() as $item) {
            if (count($item->getChildren())) {
                foreach($this->flatten($item) as $deeper) {
                    $result[] = [$compareReportRowDto->getType() => $compareReportRowDto->getLabel()] + [$item->getType() => $item->getLabel()] + $deeper;
                }
            } else {
                $result[] = [$compareReportRowDto->getType() => $compareReportRowDto->getLabel()] + [$item->getType() => $item->getLabel()] + $item->getData();
            }
        }

        return $result;
    }

您可以使用此递归函数:

function flatten($children) {
    $result = [];
    foreach($children as $child) {
        if (count($child->children) == 0) {
            $result[] = [
                $child->type => $child->id,
                "23" => $child->data->{23},
                "26" => $child->data->{26},
                "20" => $child->data->{20},
            ];
        } else {
            foreach(flatten($child->children) as $deeper) {
                $result[] = [$child->type => $child->id] + $deeper;
            }
        }
    }
    return $result;
}
假设变量
$JSON
中有JSON文本,可以按如下方式使用它:

$tree = json_decode($json);
$result = flatten($tree);
print_r($result);

请参见在第一个JSON结构中的run on

,其中有语法错误。属性名后缺少冒号,您确定属性名包含终止点吗?抱歉,现在JSON应该很好。哦,抱歉,我忘了添加一个重要的东西,它必须是递归的,因为子级可以有很多深度。更新为递归函数。