我将树结构部分存储在数据库中,并在 SQL 函数中检索它们,这是从数据库返回的数组:
$res = array(
array("uid" => "244", "part_id" => "259", "parent_part_id" => ""),
array("uid" => "245", "part_id" => "260", "parent_part_id" => "259"),
array("uid" => "246", "part_id" => "261", "parent_part_id" => "259"),
array("uid" => "247", "part_id" => "230", "parent_part_id" => "259"),
array("uid" => "248", "part_id" => "233", "parent_part_id" => "259"),
array("uid" => "249", "part_id" => "40", "parent_part_id" => "260"),
array("uid" => "251", "part_id" => "40", "parent_part_id" => "261"),
array("uid" => "252", "part_id" => "257", "parent_part_id" => "233"),
array("uid" => "250", "part_id" => "257", "parent_part_id" => "40"),
array("uid" => "254", "part_id" => "258", "parent_part_id" => "257")
);
//Wanted output:
$res = array(
array("uid" => "244", "part_id" => "259", "parent_part_id" => ""),
array("uid" => "245", "part_id" => "260", "parent_part_id" => "259"),
array("uid" => "246", "part_id" => "261", "parent_part_id" => "259"),
array("uid" => "247", "part_id" => "230", "parent_part_id" => "259"),
array("uid" => "248", "part_id" => "233", "parent_part_id" => "259"),
array("uid" => "249", "part_id" => "40", "parent_part_id" => "260"),
array("uid" => "251", "part_id" => "40.2", "parent_part_id" => "261"),
array("uid" => "250", "part_id" => "257", "parent_part_id" => "40"),
array("uid" => "254", "part_id" => "258", "parent_part_id" => "257"),
array("uid" => "250.2", "part_id" => "257.2", "parent_part_id" => "40.2"),
array("uid" => "254.2", "part_id" => "258.2", "parent_part_id" => "257.2"),
array("uid" => "252", "part_id" => "257.3", "parent_part_id" => "233"),
array("uid" => "254.3", "part_id" => "258.3", "parent_part_id" => "257.3")
);
这是我尝试过的在线 PHP 脚本, 我无法弄清楚我哪里出了问题,所以请随意撕开这个脚本:
这是我用来运行输入数组的类:
class UniqueParts
{
public function __construct($input)
{
$this->input_array = $input;
$this->return_array = [];
$this->exists = [];
}
function returnUniquePartArray()
{
//Loop through array
foreach ($this->input_array as $i) {
//if it's the first part occurrence, add to exists array and increase count by 1
if (!isset($this->exists[$i['part_id']])){
$this->exists[$i['part_id']] = 1;
$this->return_array[] = $i;
} else {
$this->exists[$i['part_id']] += 1;
$this->loopAndDuplicate($i['part_id'], $this->exists[$i['part_id']]);
$i['part_id'] = $i['part_id'].'.'.$this->exists[$i['part_id']];
$this->return_array[] = $i;
}
}
return $this->return_array;
}
private function loopAndDuplicate($pid, $count){
foreach ($this->input_array as $i){
if ($i['parent_part_id'] == $pid){
if (isset($this->exists[$i['part_id']])) {
$this->exists[$i['part_id']] += 1;
} else {
$this->exists[$i['part_id']] = 1;
}
$this->loopAndDuplicate($i['part_id'], $this->exists[$i['part_id']]);
if ($this->exists[$i['part_id']] > 1) {
$i['parent_part_id'] = $pid.'.'.$count;
$i['part_id'] = $i['part_id'] . '.' . $this->exists[$i['part_id']];
}
$this->return_array[] = $i;
}
}
}
}
转换为树结构后,如下所示:
uid = 244
part_id = 259
parent_part_id =
uid = 245
part_id = 260
parent_part_id = 259
uid = 249
part_id = 40
parent_part_id = 260
uid = 250
part_id = 257
parent_part_id = 40
uid = 254
part_id = 258
parent_part_id = 257
uid = 246
part_id = 261
parent_part_id = 259
uid = 251
part_id = 40
parent_part_id = 261
uid = 250
part_id = 257
parent_part_id = 40
uid = 254
part_id = 258
parent_part_id = 257
uid = 247
part_id = 230
parent_part_id = 259
uid = 248
part_id = 233
parent_part_id = 259
uid = 252
part_id = 257
parent_part_id = 233
uid = 254
part_id = 258
parent_part_id = 257
它正确地复制分支,但是我需要为重复的部分和分支提供唯一的part_id,然后为子级提供唯一的parent_part_id。这是我想要的打印方式:
uid = 244
part_id = 259
parent_part_id =
uid = 245
part_id = 260
parent_part_id = 259
uid = 249
part_id = 40
parent_part_id = 260
uid = 250
part_id = 257
parent_part_id = 40
uid = 254
part_id = 258
parent_part_id = 257
uid = 246
part_id = 261
parent_part_id = 259
uid = 251
part_id = 40.2
parent_part_id = 261
uid = 250.2
part_id = 257.2
parent_part_id = 40.2
uid = 254.2
part_id = 258.2
parent_part_id = 257.2
uid = 247
part_id = 230
parent_part_id = 259
uid = 248
part_id = 233
parent_part_id = 259
uid = 252
part_id = 257.3
parent_part_id = 233
uid = 254.3
part_id = 258.3
parent_part_id = 257.3
我想添加这些唯一标识符的原因是因为我使用的小部件(jqwidgets)在其树小部件中存在缺陷,因为它需要每个部分 id 键都是唯一的,以便将它们分类为单独的行。
我尝试了多个版本的递归但无济于事。我也尝试过用 MySQL 来做这件事,但我的知识还不够好。
因此,在您的
loopAndDuplicate
函数中,您正在修改 $i['part_id']
以附加计数值,但当您递归调用该函数时,它不会被保留。也许这会导致不正确的 part_id
值。
$i['part_id'] = $i['part_id'].'.'.$this->exists[$i['part_id']];
如果我对你的问题的理解没有错误,那么你定义的递归函数就不必要地复杂,并且使得跟踪计数和父部件 ID 变得困难。
因此保持构造函数相同,你可以尝试这样的事情。
在
returnUniquePartArray
中,我们从根开始处理节点。 occurences
而不是exists
public function returnUniquePartArray() {
$this->return_array = [];
$this->occurrences = [];
$this->processNode('', '');
return $this->return_array;
}
还有递归函数
processNode
-
private function processNode($parentId, $newParentPartId) {
foreach ($this->input_array as &$i) {
if ($i['parent_part_id'] == $parentId) {
$partId = $i['part_id'];
if (isset($this->occurrences[$partId])) {
$count = ++$this->occurrences[$partId];
$i['part_id'] = $partId . '.' . $count;
} else {
$this->occurrences[$partId] = 1;
$i['part_id'] = $partId;
}
$i['parent_part_id'] = $newParentPartId;
$this->return_array[] = $i;
$this->processNode($partId, $i['part_id']);
}
}
}
希望这有帮助