<?php 
/** 
    * 基于左右值排序的无限分类算法 
    * 数据库结果为 
CREATE TABLE om_catagory ( 
     CatagoryID int(10) unsigned NOT NULL auto_increment, 
    Name varchar(50) default '', 
     Lft int(10) unsigned NOT NULL default '0', 
     Rgt int(10) unsigned NOT NULL default '0', 
     PRIMARY KEY (id), 
     KEY lft (lft), 
     KEY rgt (rgt) 

    * 更多的关于左右值排序的例子 
    * http://www.chinaunix.net/jh/27/239532.html(http://dev.mysql.com/tech-resources/articles/hierarchical-data.html
    * @author [email]psdshow@yahoo.com.cn[/email] 
    * @version         1.0 
    * @copyright psdshow 
    * 欢迎光临我的个人日志 http://www.dayanmei.com 
    */ 
class sortclass 
{

/** 
    * Description 
    * @var          
    * @since         1.0 
    * @access     private 
    */ 
var $db;

/** 
    * Description 
    * @var          
    * @since         1.0 
    * @access     private 
    */ 
var $tablefix;

/** 
    * Short description. 
    * 构造函数,引入数据库操作类函数 
    * Detail description 
    * @param         none 
    * @global         none 
    * @since         1.0 
    * @access         private 
    * @return         void 
    * @update         date time 
*/ 
function sortclass() 

global $db; 
$this->db=$db; 
$this->tablefix="om_"; 
} // end func

/** 
    * Short description. 
    * 增加新的分类 
    * Detail description 
    * @param         none 
    * @global         none 
    * @since         1.0 
    * @access         private 
    * @return         void 
    * @update         date time 
*/ 
function addsort($CatagoryID,$SortName) 

if($CatagoryID==0){ 
    $Lft=0; 
    $Rgt=1; 
    }else{ 
    $Result=$this->checkcatagory($CatagoryID); 
    //取得父类的左值,右值 
    $Lft=$Result['Lft']; 
    $Rgt=$Result['Rgt']; 
    $this->db->query("UPDATE `".$this->tablefix."catagory` SET `Lft`=`Lft`+2 WHERE `Lft`>$Rgt"); 
    $this->db->query("UPDATE `".$this->tablefix."catagory` SET `Rgt`=`Rgt`+2 WHERE `Rgt`>=$Rgt"); 
    }

//插入 
if($this->db->query("INSERT INTO `".$this->tablefix."catagory` SET `Lft`='$Rgt',`Rgt`='$Rgt'+1,`Name`='$SortName'")){ 
    //$this->referto("成功增加新的类别","JAVASCRIPT:HISTORY.BACK(1)",3); 
    return 1; 
    }else{ 
    //$this->referto("增加新的类别失败了","JAVASCRIPT:HISTORY.BACK(1)",3); 
    return -1; 
    } 
} // end func

/** 
    * Short description. 
    * 删除类别 
    * Detail description 
    * @param         none 
    * @global         none 
    * @since         1.0 
    * @access         private 
    * @return         void 
    * @update         date time 
*/ 
function deletesort($CatagoryID) 

//取得被删除类别的左右值,检测是否有子类,如果有就一起删除 
$Result=$this->checkcatagory($CatagoryID); 
$Lft=$Result['Lft']; 
$Rgt=$Result['Rgt']; 
//执行删除 
if($this->db->query("DELETE FROM `".$this->tablefix."catagory` WHERE `Lft`>=$Lft AND `Rgt`<=$Rgt")){ 
    $Value=$Rgt-$Lft+1; 
    //更新左右值 
    $this->db->query("UPDATE `".$this->tablefix."catagory` SET `Lft`=`Lft`-$Value WHERE `Lft`>$Lft"); 
    $this->db->query("UPDATE `".$this->tablefix."catagory` SET `Rgt`=`Rgt`-$Value WHERE `Rgt`>$Rgt"); 
    //$this->referto("成功删除类别","javascript:history.back(1)",3); 
    return 1; 
    }else{ 
    //$this->referto("删除类别失败了","javascript:history.back(1)",3); 
    return -1; 
    } 
} // end func

/** 
    * Short description. 
    * 1,所有子类,不包含自己;2包含自己的所有子类;3不包含自己所有父类4;包含自己所有父类 
    * Detail description 
    * @param         none 
    * @global         none 
    * @since         1.0 
    * @access         private 
    * @return         void 
    * @update         date time 
*/ 
function getcatagory($CatagoryID,$type=1) 

$Result=$this->checkcatagory($CatagoryID); 
$Lft=$Result['Lft']; 
$Rgt=$Result['Rgt']; 
$SeekSQL="SELECT * FROM `".$this->tablefix."catagory` WHERE "; 
switch ($type) { 
     case "1": 
    $condition="`Lft`>$Lft AND `Rgt`<$Rgt"; 
    break; 
    case "2": 
    $condition="`Lft`>=$Lft AND `Rgt`<=$Rgt"; 
    break; 
     case "3": 
         $condition="`Lft`<$Lft AND `Rgt`>$Rgt"; 
         break; 
    case "4": 
    $condition="`Lft`<=$Lft AND `Rgt`>=$Rgt"; 
    break; 
    default : 
    $condition="`Lft`>$Lft AND `Rgt`<$Rgt"; 
    ; 
    } 
$SeekSQL.=$condition." ORDER BY `Lft` ASC"; 
$Sorts=$this->db->getrows($SeekSQL); 
return $Sorts; 
} // end func

/** 
    * Short description. 
    * 取得直属父类 
    * Detail description 
    * @param         none 
    * @global         none 
    * @since         1.0 
    * @access         private 
    * @return         void 
    * @update         date time 
*/ 
function getparent($CatagoryID) 

$Parent=$this->getcatagory($CatagoryID,3); 
return $Parent; 
} // end func 
/** 
    * Short description. 
    * 移动类,如果类有子类也一并移动 
    * Detail description 
    * @param         none 
    * @global         none 
    * @since         1.0 
    * @access         private 
    * @return         void 
    * @update         date time 
*/ 
function movecatagory($SelfCatagoryID,$ParentCatagoryID) 

$SelfCatagory=$this->checkcatagory($SelfCatagoryID); 
$NewCatagory=$this->checkcatagory($ParentCatagoryID);

$SelfLft=$SelfCatagory['Lft']; 
$SelfRgt=$SelfCatagory['Rgt']; 
$Value=$SelfRgt-$SelfLft; 
//取得所有分类的ID方便更新左右值 
$CatagoryIDS=$this->getcatagory($SelfCatagoryID,2); 
foreach($CatagoryIDS as $v){ 
    $IDS[]=$v['CatagoryID']; 
    } 
$InIDS=implode(",",$IDS);

$ParentLft=$NewCatagory['Lft']; 
$ParentRgt=$NewCatagory['Rgt']; 
//print_r($InIDS); 
//print_r($NewCatagory); 
//print_r($SelfCatagory); 
//exit; 
if($ParentRgt>$SelfRgt){ 
    $UpdateLeftSQL="UPDATE `".$this->tablefix."catagory` SET `Lft`=`Lft`-$Value-1 WHERE `Lft`>$SelfRgt AND `Rgt`<=$ParentRgt"; 
    $UpdateRightSQL="UPDATE `".$this->tablefix."catagory` SET `Rgt`=`Rgt`-$Value-1 WHERE `Rgt`>$SelfRgt AND `Rgt`<$ParentRgt"; 
    $TmpValue=$ParentRgt-$SelfRgt-1; 
    $UpdateSelfSQL="UPDATE `".$this->tablefix."catagory` SET `Lft`=`Lft`+$TmpValue,`Rgt`=`Rgt`+$TmpValue WHERE `CatagoryID` IN($InIDS)"; 
    }else{ 
    $UpdateLeftSQL="UPDATE `".$this->tablefix."catagory` SET `Lft`=`Lft`+$Value+1 WHERE `Lft`>$ParentRgt AND `Lft`<$SelfLft"; 
    $UpdateRightSQL="UPDATE `".$this->tablefix."catagory` SET `Rgt`=`Rgt`+$Value+1 WHERE `Rgt`>=$ParentRgt AND `Rgt`<$SelfLft"; 
    $TmpValue=$SelfLft-$ParentRgt; 
    $UpdateSelfSQL="UPDATE `".$this->tablefix."catagory` SET `Lft`=`Lft`-$TmpValue,`Rgt`=`Rgt`-$TmpValue WHERE `CatagoryID` IN($InIDS)"; 
    } 
$this->db->query($UpdateLeftSQL); 
$this->db->query($UpdateRightSQL); 
$this->db->query($UpdateSelfSQL); 
//$this->referto("成功移动类别","javascript:history.back(1)",3); 
return 1; 
} // end func

/** 
    * Short description. 
    * 
    * Detail description 
    * @param         none 
    * @global         none 
    * @since         1.0 
    * @access         private 
    * @return         void 
    * @update         date time 
*/ 
function checkcatagory($CatagoryID) 

//检测父类ID是否存在 
$SQL="SELECT * FROM `".$this->tablefix."catagory` WHERE `CatagoryID`='$CatagoryID' LIMIT 1"; 
$Result=$this->db->getrow($SQL); 
if(count($Result)<1){ 
    $this->referto("父类ID不存在,请检查","javascript:history.back(1)",3); 
    } 
return $Result;      
} // end func

/** 
    * Short description. 
    * 
    * Detail description 
    * @param         none 
    * @global         none 
    * @since         1.0 
    * @access         private 
    * @return         array($Catagoryarray,$Deep) 
    * @update         date time 
*/ 
function sort2array($CatagoryID=0) 

     $Output = array(); 
     if($CatagoryID==0){ 
    $CatagoryID=$this->getrootid(); 
    } 
     if(empty($CatagoryID)){ 
    return array(); 
    exit; 
    } 
     $Result = $this->db->query('SELECT Lft, Rgt FROM `'.$this->tablefix. 
                                 'catagory` WHERE `CatagoryID`='.$CatagoryID); 
     if($Row = $this->db->fetch_array($Result)) { 
     $Right = array(); 
     $Query = 'SELECT * FROM `'.$this->tablefix. 
                 'catagory` WHERE Lft BETWEEN '.$Row['Lft'].' AND '. 
                 $Row['Rgt'].' ORDER BY Lft ASC'; 
      
     $Result = $this->db->query($Query); 
     while ($Row = $this->db->fetch_array($Result)) { 
         if (count($Right)>0) { 
    while ($Right[count($Right)-1]<$Row['Rgt']) { 
    array_pop($Right); 
    } 
         } 
    $Output[]=array('Sort'=>$Row,'Deep'=>count($Right)); 
     $Right[] = $Row['Rgt']; 
     } 
     } 
     return $Output;      
} // end func

/** 
    * Short description. 
    * 
    * Detail description 
    * @param         none 
    * @global         none 
    * @since         1.0 
    * @access         private 
    * @return         void 
    * @update         date time 
*/ 
function getrootid() 

$Query="SELECT * FROM`".$this->tablefix."catagory` ORDER BY `Lft` ASC LIMIT 1"; 
$RootID=$this->db->getrow($Query); 
if(count($RootID)>0){ 
    return $RootID['CatagoryID']; 
    }else{ 
    return 0; 
    } 
} // end func

/** 
    * Short description. 
    * 
    * Detail description 
    * @param         none 
    * @global         none 
    * @since         1.0 
    * @access         private 
    * @return         void 
    * @update         date time 
*/ 
function referto($msg,$url,$sec) 

    echo "<meta http-equiv=\"Content-Type\" content=\"text/html; charset=utf-8\">"; 
    echo "<meta http-equiv=refresh content=$sec;URL=$url>"; 
         if(is_array($msg)){2881064151 
    foreach($msg as $key=>$value){ 
    echo $key."=>".$value."<br>"; 
             } 
             }else{ 
             echo $msg; 
             } 
     exit; 
} // end func 
} // end class

?>

函数描述及例子

PHP无限分类[左右值]算法

php构造函数,引入数据库操作类函数的更多相关文章

  1. asp.net+mysq 数据库操作类

    对数据库操作的使用方法: 1.引入命名空间 2.操作.三四行代码即可完成数据操作.类似于: using System; using System.Data; using System.Text; us ...

  2. net core Webapi基础工程搭建(六)——数据库操作_Part 2

    目录 前言 开始 使用 小结 前言 昨天是写着写着发现,时间不早了,已经养成了晚上下班抽时间看看能写点儿啥的习惯(貌似),今天实在是不想让昨天没做完的事情影响,所以又坐下,沉下心(周末了),开始把数据 ...

  3. net core Webapi基础工程搭建(六)——数据库操作_Part 1

    目录 前言 SqlSugar Service层 BaseService(基类) 小结 前言 后端开发最常打交道的就是数据库了(静态网站靠边),上一篇net core Webapi基础工程搭建(五)-- ...

  4. Java数据库操作学习

    JDBC是java和数据库的连接,是一种规范,提供java程序与数据库的连接接口,使用户不用在意具体的数据库.JDBC类型:类型1-JDBC-ODBC桥类型2-本地API驱动类型3-网络协议驱动类型4 ...

  5. 【第一篇】ASP.NET MVC快速入门之数据库操作(MVC5+EF6)

    目录 [第一篇]ASP.NET MVC快速入门之数据库操作(MVC5+EF6) [第二篇]ASP.NET MVC快速入门之数据注解(MVC5+EF6) [第三篇]ASP.NET MVC快速入门之安全策 ...

  6. Android打造属于自己的数据库操作类。

    1.概述 开发Android的同学都知道sdk已经为我们提供了一个SQLiteOpenHelper类来创建和管理SQLite数据库,通过写一个子类去继承它,就可以方便的创建.管理数据库.但是当我们需要 ...

  7. PHP数据库操作:使用ORM

    之前我发了一篇博文PHP数据库操作:从MySQL原生API到PDO,向大家展示PHP是如何使用MySQL原生API.MySQLi面向过程.MySQLi面向对象.PDO操作MySQL数据库的.本文介绍如 ...

  8. PHP中对数据库操作的封装

    在动态网面设计中很多都要涉及到对数据库的操作,但是有时跟据需要而改用其它后台数据库,就需要大量修改程序.这是一件枯燥.费时而且容易出错的功作.其实我们可以用PHP中的类来实现对数据库操作的封装,从而使 ...

  9. iOS学习笔记(十五)——数据库操作(SQLite)

    SQLite (http://www.sqlite.org/docs.html) 是一个轻量级的关系数据库.SQLite最初的设计目标是用于嵌入式系统,它占用资源非常少,在嵌入式设备中,只需要几百K的 ...

随机推荐

  1. mysql cluster 运行的必备条件

    1.由于同步复制一共需要4次消息传递,故mysql  cluster的数据更新速度比单机mysql要慢.所以mysql cluster要求运行在千兆以上的局域网内,节点可以采用双网卡,节点组之间采用直 ...

  2. Java for LeetCode 053 Maximum Subarray

    Find the contiguous subarray within an array (containing at least one number) which has the largest ...

  3. Java for LeetCode 044 Wildcard Matching

    Implement wildcard pattern matching with support for '?' and '*'. '?' Matches any single character. ...

  4. 12.python笔记之mysqldb模块

    一.使用python调用模块操作MYsql 2.x版本使用mysqldb模块 3.x版本使用pymysql模块 1.数据库常用操作: 使用Navicat for MySql软件来操作 show dat ...

  5. 【USACO】calfflac

    关键:以回文中心位置为变量进行遍历 //必须把纯字母先提出来 否则肯能会出现错误 比如: lvlv= 在检查长度4时 lvlv认为不是回文 vlv=认为是回文 但实际上 lvl 出现的要更早一些 // ...

  6. SGU 106 The equation

    H - The equation Time Limit:250MS     Memory Limit:4096KB     64bit IO Format:%I64d & %I64u Subm ...

  7. [Android Pro] PackageManager#getPackageSizeInfo (hide)

    referce to : http://www.baidufe.com/item/8786bc2e95a042320bef.html 计算Android App所占用d的手机内存(RAM)大小.App ...

  8. onItemClick 参数解释

    X, Y两个listview,X里有1,2,3,4这4个item,Y里有a,b,c,d这4个item.如果你点了b这个item.如下:public void onItemClick (AdapterV ...

  9. 消息队列入门(三)JMS标准及实现

    >>消息中间件 消息中间件即Message-oriented middleware(MOM),消息中间件利用高效可靠的消息传递机制进行平台无关的数据交流,并基于数据通信来进行分布式系统的集 ...

  10. 项目如何脱离TFS 2010的管理

    在VS 里,文件->源代码管理->更改源代码管理->取消绑定.