php数组无限文类,理解PHP无限级分类

无限级分类知识点其实理解起来比较简单。因为在实际的项目中比如典型的如电商网站、一些CMS内容发布站点等都会涉及到无限级分类的知识。所以这篇文章准备用原生PHP代码来简单的现实一些典型的无限级分类。本次文章记录的是在实验楼这个网站上的一个实验经历,整理成自己的博文

实验环境PHP 7.0.12

CentOS7.4

MySQL 5.7

Web服务器就使用PHP内置的Server,直接在项目根目录下执行php -S 127.0.0.1:8080就可以,然后通过http://127.0.0.1:8080来进行访问即可。

代码仓库待补充(gitee)

实验介绍

本次介绍的无限级分类采用省市结构的方式来展示,如下图

document-uid79217labid2282timestamp1478574987484.png

最终的效果如下面图片所展示

document-uid79217labid2282timestamp1479099771956.png

创建数据库、表

首先我们建立一个简单的数据表,用来存放上面的省市结构数据。表结构SQL如下create database category;

CREATE TABLE `category` (

`id` int(11) NOT NULL AUTO_INCREMENT COMMENT '自动增长id',

`pid` int(11) NOT NULL COMMENT '父id',

`category` varchar(255) NOT NULL COMMENT '分类名称',

`orderid` int(11) NOT NULL DEFAULT '0' COMMENT '排序id',

PRIMARY KEY (`id`)

) ENGINE=InnoDB DEFAULT CHARSET=utf8;

然后我们往表里初始化一些数据,方便页面显示。INSERT INTO `category` VALUES ('1', '0', '中国', '0');

INSERT INTO `category` VALUES ('2', '1', '河北', '0');

INSERT INTO `category` VALUES ('3', '1', '山西', '0');

INSERT INTO `category` VALUES ('4', '2', '石家庄', '0');

INSERT INTO `category` VALUES ('5', '2', '邯郸', '0');

INSERT INTO `category` VALUES ('6', '3', '太原', '0');

INSERT INTO `category` VALUES ('7', '3', '大同', '0');

INSERT INTO `category` VALUES ('8', '4', '桥东', '0');

INSERT INTO `category` VALUES ('9', '4', '桥西', '0');

INSERT INTO `category` VALUES ('10', '5', '邯山', '0');

INSERT INTO `category` VALUES ('11', '5', '丛台', '0');

INSERT INTO `category` VALUES ('12', '6', '小店', '0');

INSERT INTO `category` VALUES ('13', '6', '迎泽', '0');

INSERT INTO `category` VALUES ('14', '7', '南郊', '0');

INSERT INTO `category` VALUES ('15', '7', '新荣', '0');

数据库DB类

我们简单的封装一下DB类,以便于后面的整体复用。DB类我们采用单例的模式,以避免重复的创建数据库实例。

这里提一下单例模式3个要点要声明一个静态变量来存储这个实例

类的构造函数必须为私有

必须建立一个获取实例的方法

那么首先创建一个db.php,内容大致如下。<?php

class db

{

//私有变量保存实例

private static $_instance;

//定义一个私有静态变量保存数据库连接

private static $_conn;

private function __construct() {}

//定义获取数据库实例的方法

public static function getInstance()

{

if (self::$_instance === null) {

self::$_instance = new self();

}

return self::$_instance;

}

public static function connect()

{

if (! self::$_conn) {

self::$_conn = new mysqli('127.0.0.1', 'root', 'root', 'category');

}

mysqli_query(self::$_conn, "set names UTF8");

return self::$_conn;

}

}

编写好db类以后,可以使用下面一段简单的代码来测试下是否可以正常连接到数据库。<?php

include 'db.php';

$db = db::getInstance()->connect();

$result = $db->query("select * from category");

while ($row = $result->fetch_assoc()) {

echo $row['id'] . ':' . $row['category'] . '
';

}

output:

1:中国

2:河北

3:山西

4:石家庄

5:邯郸

6:太原

...

分类列表展示页面(index.php)

由于在分类列表展示页面中我们需要获取所有分类列表数据,所以我们使用递归的方式来获取这个数组。首先建立一个function.php文件。编写一个getCate方法function getCate($pid = 0, &$result = array(), $s = 0)

{

// 分类层级前展示的空格数

$s = $s + 4;

$conn = db::getInstance()->connect();

//获取数据对象

$sql = "SELECT * FROM `category` where `pid` = $pid";

$res = $conn->query($sql);

while ($row = $res->fetch_assoc()) {

$row['category'] = str_repeat("&nbsp", $s) . '|--' . $row['category'];

$result[] = $row;

getCate($row['id'], $result, $s);

}

return $result;

}

上面这个就是使用递归算法来获取所有的层级分类

函数中有三个参数:第一个参数是查父ID的所有分类。

第二个参数把查到的数据及所有的自己放到这个数组地址中来。

第三个是我们每次层级深度前面的加的空格数。

执行步骤:第一步是执行查询pid为0的所有子类,放到 resqult[] 数组中。

第二步是循环查找第一步查出的子类,pid 为子类的 ID。查出的所有的子类,并放到 resqult[] 数组中。

最后查出分类没有子类后,循环不成立,不能继续执行 getCate 函数,此时函数已经不再调用自己,开始将流程的主控权交回给上一层函数来执行,开始执行所有的数据:return $resault。

最后编写index.php页面内容,如下<?php

require_once('./db.php');

require_once('function.php');

?>

分类管理

添加分类

id分类名操作

$rs = getCate();

foreach ($rs as $key => $value) {

?>

<?php echo $value['id'] ?><?php echo $value['category'] ?> 编辑 | 删除

}

?>

document-uid79217labid2282timestamp1479099108333.png

添加分类页面

建立一个名为categoryadd.php页面,内容如下<?php

require_once('./db.php');

require_once('function.php');

$conn = db::getInstance()->connect();

// $result = $conn-> query("select * from category");

$result = getCate();

// dd($result->fetch_assoc());

?>

添加分类

上级菜单

作为顶级菜单

分类名称

效果图如下

document-uid79217labid2282timestamp1479099130351.png

这里主要也是调用了getCate函数来获取到上级菜单列表,然后展示出来。分类添加的数据处理,我们稍后在编写。

分类编辑页面

在管理页面,我们可以对每条分类进行编辑操作,所以需要创建一个页面来实现分类的编辑更新操作。在项目目录下,新建categoryedit.php,编辑如下:

数据处理页面

最后到了数据的入库、编辑等操作了。所以我们创建一个action.php的文件来处理前台提交过来的数据,如下:<?php

require_once 'db.php';

require_once 'function.php';

$action = $_GET['action'];

switch ($action) {

case 'add':

$pid = $_POST['pid'];

$category = $_POST['category'];

categoryAdd($pid, $category);

break;

case 'update':

$id = $_POST['id'];

$pid = $_POST['pid'];

$category = $_POST['category'];

categoryUpdate($id, $pid, $category);

break;

case 'del':

$id = (int)$_GET['id'];

categoryDel($id);

break;

default:

exit('非法操作');

}

function categoryAdd($pid, $category) {

$conn = db::getInstance()->connect();

$sql = "INSERT INTO `category` (`pid`, `category`) VALUES ({$pid}, '{$category}')"; //注意string类型要加单引号

// echo $sql;exit;

$res = $conn->query($sql);

if ($res) {

echo "";

exit;

} else {

echo "";

}

}

function categoryDel($id) {

$conn = db::getInstance()->connect();

//查询当前分类下是否有子分类

$sql = "SELECT count(*) AS `count` FROM `category` WHERE `pid` = '{$id}'";

$res = $conn->query($sql);

$result = $res->fetch_array();

if ($result[0] > 0) {

echo "";

exit;

} else {

//删除操作

$sql = "DELETE FROM `category` WHERE `id` = '{$id}'";

$res = $conn->query($sql);

if ($res) {

echo "";

}

}

}

function categoryUpdate($id, $pid, $category) {

$conn = db::getInstance()->connect();

$sql = "UPDATE `category` SET `pid` = '{$pid}', `category` = '{$category}' WHERE `id` = '{$id}'";

$res = $conn->query($sql);

if ($res) {

echo "";

}

}

这个action.php文件主要就是接受不同的动作、接受前台提交过来的数据,然后拼接SQL语句以后执行对应的数据库操作。注意:在拼接sql语句的时候要主要字符串类型的数据需要加引号('),不然语句无法执行成功。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值