ツリー構造を実装する 2 つの方法
1.再帰メソッド
再帰とは、関数内でそれ自体を明示的に呼び出すことを意味します。
再帰的手法を使用してツリー構造を実現すると、データの書き込み速度が速くなり、表示速度が遅くなるという特徴があります (特にツリーに多くの分岐/レベルがある場合に顕著です)。書き込むデータ量が多く、ツリー構造が複雑な場合に適しています。
データ構造 (mysql を例にします)
コード:---------------------------- ---------------------------------------------------- ----
CREATE TABLE `tree1` (
`id` tinyint(3) unsigned NOT NULL auto_increment,
`parentid` tinyint(3) unsigned NOT NULL デフォルト '0',
` topic` varchar(50 ) デフォルト NULL,
PRIMARY KEY (`id`),
KEY `parentid` (`parentid`)
) TYPE=MyISAM;
INSERT INTO `tree1 ` (`id` 、`parentid`、`topic`) 値
(1,0,'ツリー 1')、
(2,0,'ツリー 2')、
(3,0 ,'ツリー 3' ),
(4,2,'ツリー 2-1'),
(5,4,'ツリー 2-1-1'),
(6,2,'ツリー 2-2' )、
(7,1,'ツリー 1-1')、
(8,1,'ツリー 1-2')、
(9,1,'ツリー 1 -3')、
(10,8,'ツリー 1-2-1')、
(11,7,'ツリー 1-1-1')、
(12,11,'ツリー 1-1- 1-1');
------------------------------------- ----- --------------------------------------
フィールドの説明
id、レコードの ID 番号
parentid、レコードの親レコード ID (0 の場合はルート レコード)
トピック、トピックの表示タイトルレコード
表示プログラム
シーケンスツリー:
PHP コード:---------------------- ------------------ -------------------------------- ----------
< ?
/* データベース接続*/
mysql_connect();
mysql_select_db('tree');
/* 再帰関数をツリー形式で表示*/
function Tree($parentid = 0) {
/*SQL クエリを実行してレコードのタイトルと ID を取得*/
$sql = "select topic,id fromtree1 whereparentid = $parentid order by id asc";
$ rs = mysql_query($sql);
/* Indent*/
echo("
");
while($ra = mysql_fetch_row($rs)) {
/* レコードのタイトルを表示*/
echo('- '.$ra[0].'
') ;
/* 再帰呼び出し*/
tree($ra[1 ]);
}
echo("
");
}
tree() ;
?>
------ ----------------------------- ------------------- ------------------------
逆ツリー:
PHP コード:----- ----------------------------- ------------------------ ------------------------
/* データベース接続*/
mysql_connect();
mysql_select_db('tree');
/* ツリー表示用の再帰関数*/
関数ツリー($parentid = 0) {
/*SQL クエリを実行してレコードのタイトルと ID を取得*/
$sql = "select topic,id fromtree1 whereparentid = $parentid order by id desc";
$rs = mysql_query($sql);
/* インデント*/
echo("
");
while($ra = mysql_fetch_row($rs)) {
/ * レコードのタイトルを表示*/
echo('- '. $ra[0].'
');
/* 再帰呼び出し*/
;");
}
tree();
?>
---------------------- ---- ------------------------------------------------ ---- ---
データプログラムの挿入
PHP コード:---------------------- ---- ------------------------------------------------ ---- ----
/* データベース接続*/
mysql_connect();
mysql_select_db('tree');
$sql = " ツリーに挿入 ( topic,parentid) value('tree 3-1',3);";
mysql_query($sql);
?>
------ ----- -------------------------------------- ----- ------------------
2.並べ替えフィールド メソッド
このメソッドは、ツリー全体におけるレコードの連続位置をマークするフィールドをデータ構造に追加することによって実装されます。表示速度と効率が高いのが特徴です。しかし、単一ツリーの構造が複雑になると、データの書き込み効率が不十分になる。また、順番に並べる場合、レコードの挿入や削除のアルゴリズムが複雑すぎるため、通常は逆順が使用されます。
データ構造 (mysql を例にします)
コード: ------------------------- -------------------------------------------------- - --
CREATE TABLE `tree2` (
`id` tinyint(3) unsigned NOT NULL auto_increment,
`parentid` tinyint(3) unsigned NOT NULL デフォルト '0',
`rootid ` tinyint(3) unsigned NOT NULL デフォルト '0',
`layer` tinyint(3) unsigned NOT NULL デフォルト '0',
`orders` tinyint(3) unsigned NOT NULL デフォルト '0',
`topic` varchar(50) デフォルト NULL,
PRIMARY KEY (`id`),
KEY `parentid` (`parentid`),
KEY `rootid` (`rootid`)
) TYPE=MyISAM
INSERT INTO `tree2` (`id`, `parentid`, `rootid`, `layer`, `orders`, `topic`) VALUES
(1,0, 1 ,0,0,'ツリー 1'),
(2,0,2,0,0,'ツリー 2'),
(3,0,3,0,0,'ツリー 3' ) 、
(4,2,2,1,2,'ツリー 2-1')、
(5,4,2,2,3,'ツリー 2-1-1')、
(6,2,2,1,1,'ツリー 2-2'),
(7,1,1,1,4,'ツリー 1-1'),
(8,1, 1 ,1,2,'ツリー 1-2'),
(9,1,1,1,1,'ツリー 1-3'),
(10,8,1,2,3, ' ツリー 1-2-1'),
(11,7,1,2,5,'ツリー 1-1-1'),
(12,11,1,3,6,'ツリー1 -1-1-1');
------------------------------------- ----------------------------------------------------
表示プログラム
PHP コード:--------------------------------- --------------------------------------
< ?
/* データベース接続*/
mysql_connect();
mysql_select_db('tree');
/* すべてのルート レコード ID を選択します */
$sql = " select id from Tree2 whereparentid = 0 order by id desc";
$rs = mysql_query($sql);
echo("");
$lay = 0;
while($ra = mysql_fetch_row($rs)) {
echo("");
/* このツリー内のすべてのレコードを選択し、注文フィールドで並べ替えます*/
$sql = "ツリー 2 からトピック、レイヤーを選択します。ここで rootid = $ra[0] 注文順に並べ替えます";
$rs1 = mysql_query($sql);
while($ra1 = mysql_fetch_row($rs1) ) {
/* インデント表示*/
if($ra1[1]>$lay) {
echo(str_repeat("",$ra1[1]-$lay) );
}elseif($ra1[1]<$lay) {
echo(str_repeat("
",$lay-$ra1[1]));
記録表示*/
//echo("$ra1[1]>$lay") ; $lay = $ra1[1];
}
echo("
");
}
echo("
");
?> ;
--------------------- ------------------------ ------------------------ --------------
データ プログラムの挿入
PHP コード:-------------- ------------------------------ -------------------- -----------------
/* データベース接続*/
mysql_connect();
mysql_select_db('tree' );
/* ルート レコードを挿入*/
$sql = "ツリー 2 (トピック) の値 ('tree5') に挿入";
mysql_query($sql);
$sql = "update Tree2 set rootid = id where id = ".mysql_insert_id();
mysql_query($sql);
/* 子レコードを挿入*/
$parentid = 5;//親Record ID
/* ルート レコード ID、親レコードのインデント レベル、親レコード シーケンス位置を削除します*/
$ sql = "select rootid,layer,orders from Tree2 where id = $parentid";
list( $rootid,$layer,$orders) = mysql_fetch_row(mysql_query($sql));
/* 挿入位置を更新 最後のレコードのorders値*/
$sql = "updatetree2 setorders =orders 1 where order > $orders";
mysql_query($sql);
/* レコードを挿入*/
$sql = "tree2 (rootid,parentid,orders,layer,topic) の値に挿入($rootid,$parentid,".($orders 1).",".($layer 1).",'tree2- 1-1-2')";
mysql_query($sql);?> ;