0

我有 4 个表被设置为具有分层数据。我正在尝试通过连接取回数据,并找到一种可重用的方法来从结果中获取多维数组,将来我可能会使用不同的表布局。最终我想把它作为 json 吐出来。有没有好的方法来做到这一点?

这是我的 mySQL 代码的示例:

SELECT 

    table1.name as level1_name,
    table1.id as level1_id,
    table2.name as level2_name,
    table2.id as level2_id,
    table3.name as level3_name,
    table3.id as level3_id,
    table4.name as level4_name,
    table4.id as level4_id

FROM
    table1

LEFT JOIN table2    on table2.parentid      = table1.id
LEFT JOIN table3    on table3.parentid      = table2.id
LEFT JOIN table4    on table4.parentid      = table3.id

WHERE
    table1.id = 5

我希望看到这样的结果:

Table1_name
{
    Table2_name {
        Table3_name {
            Table4_name,
            Table4_othername
        }
    }
    Table2_othername {
        Table3_othername {
            Table4_othername,
            Table4_otherothername
        }
    }
}

但我得到的是:

Array
(
    [0] => stdClass Object
        (
            [level1_name] => Lorem
            [level1_id] => x
            [level2_name] => Ipsum
            [level2_id] => x
            [level3_name] => Dolor
            [level3_id] => x
            [level4_name] => Eimet
            [level4_id] => x
        )

    [1] => stdClass Object
        (
            [level1_name] => Lorem
            [level1_id] => x
            [level2_name] => Ipsum
            [level2_id] => x
            [level3_name] => Dolor
            [level3_id] => x
            [level4_name] => Eimet
            [level4_id] => x
        )

    [2] => stdClass Object
        (
            [level1_name] => Lorem
            [level1_id] => x
            [level2_name] => Ipsum
            [level2_id] => x
            [level3_name] => Dolor
            [level3_id] => x
            [level4_name] => Eimet
            [level4_id] => x
        )
)
4

2 回答 2

0

正如其他人所提到的,普通的 SQL 不会让你通过这个。要生成这样一个数组,您需要遍历每个主行的所有详细记录。

您需要的是一个递归函数,它为主/细节层次结构的每个级别构造相应的数组。

但在此之前,请考虑以下事项:

function get_table($table,$field=null,$value=null)
  {
  ....
  }

这应该从关联数组的数组中返回指定的所有数据$table,前提$fieldnull. 如果不是,它应该应用where $field=$value过滤器。

现在,到多汁的部分。以下函数将遍历主/明细表层次结构,基于$details数组并以 开头$table,可能由 过滤$field=$value

function table_tree($table,$arrkey,$details=array(),$field=null,$value=null)    
  {
  $detail=array_shift($details);
  $r=array();
  foreach(get_table($table,$field,$value) as $row)
    {
    $label=$row[$arrkey];
    if($detail)
      $r[$label]=table_tree(
        $detail['table'],
        $detail['label'],
        $details,
        $detail['detailkey'],
        $row[$detail['masterkey']]
        );
    else
      $r[]=$label;
    }
  return $r;
  }

现在,$details参数应该是以下形式的数组:

array(
  array('table'=>..., 'label'=>..., 'detailkey'=>..., 'masterkey'=>...),
  /* etc */
  );

每个详细级别都应该有一个条目,其中包含以下字段:

  • table: 明细表名

  • label:应该用于生成数组键的字段

  • detailkey:将明细行链接到主行的字段

  • masterkey:主表的字段,用于过滤明细

对于您的示例,您需要执行以下操作:

$master_table='table1';
$hierarchy=array(
  array('table'=>'table2','label'=>'name','detailkey'=>'parentid','masterkey'=>'id'),
  array('table'=>'table3','label'=>'name','detailkey'=>'parentid','masterkey'=>'id'),
  array('table'=>'table4','label'=>'name','detailkey'=>'parentid','masterkey'=>'id'),
  );
$result=table_tree($master_table,'name',$hierarchy);

就是这样。我希望它对你有帮助。

于 2013-09-27T21:27:59.973 回答
0

要么分开你的查询。或者使用字段名称的前缀将它们添加到不同的对象中将 level1_id 重命名为 level_1_id 这样使用explode和几个for循环更容易解析数字

于 2013-09-25T18:02:27.890 回答