1.对&引用传值的小例子
$age =10;
function sum($age){
$age+=5;
return $age;
}
echo sum(&$age).'<br>'; //引用传值,输出15
echo $age; //输出 15
//----------------------------------------------
function sum($age){
$age+=5;
return $age;
}
echo sum($age).'<br>'; //输出15
echo $age; //输出 10
引用传值,函数内部的$age 和全局的$age 指向了同一个变量地址。因此内部变化了,外部也跟着变化。破坏了函数的封装性,一般不推荐引用传参。
5.4版php已经删除此功能。5.3解决此问题 php.ini allow_call_time_pass_reference=off
2、递归转义
//递归转义
function _addslashes($arr){
foreach($arr as $k=>$v){
if(is_string($v)){//判断是否是字符串
$arr[$k] = addslashes($v);
}else if(is_array($v)){//判断是否是数组
$arr[$k] = _addslashes($v);
}
}
return $arr;
}
$arr = array('a"b',array('b\b',"c'd'"));
print_r(_addslashes($arr));
3、utf8编码 中文截取无乱码
$str = '中华人aaaa民共和国';
/*
$str 需要截取的字符串
$len 需要截取的字符数
*/
function utf8sub($str,$len){
//长度等于0
if($len <= 0){
return '';
}
$length = strlen($str); //最多字符串长度
//先截取字符串的第一个字节 用substr
// ord() 返回ASCall码值 decbin转化成二进制
$char = 0;//已经截取的字符数
$res = '';//已经截取的字符串
$offset = 0;//偏移量,既第二次截取时从第几个字节开始
while($char < $len && $offset < $length){
$high = decbin(ord(substr($str,$offset,1)));//取得转化后的高位
echo $high.'<br>';
if(strlen($high) < 8){ //截取1个字节
$count = 1;
}else if(substr($high,0,3) == '110'){
$count = 2;//截取2个字节
}else if(substr($high,0,4) == '1110'){
$count = 3;//截取3个字节
}else if(substr($high,0,5) == '11110'){
$count = 4;//截取4个字节
}else if(substr($high,0,6) == '111110'){
$count = 5;//截取4个字节
}else if(substr($high,0,7) == '111111'){
$count = 6;//截取4个字节
}
$res .= substr($str,$offset,$count);
$offset +=$count;
$char +=1;
}
return $res;
}
echo utf8sub($str,8);
4、查找子孙树。
//递归查找子孙树
function subtree($arr,$id = 0,$lev=1){
if(!is_array($arr)){
return $arr;
}
static $sub = array();//如果不用静态变量。则可以下面$sub = array_merge($sub,subtree($arr,$v['id'],$lev+1);
foreach($arr as $v){
if($v['parent'] == $id){
$v['lev'] = $lev;
$sub[] = $v;
$sub = subtree($arr,$v['id'],$lev+1);
}
}
return $sub;
}
echo '<pre>';
//print_r(subtree($area,0));
$new = subtree($area,0);
foreach($new as $v){
echo str_repeat(' ',$v['lev']).$v['name'].'<br>';
}
5、查找家谱树树
function familyTree($arr,$id){
$tree = array();
foreach($arr as $v){
if($v['id'] == $id){ //找到$id
//判断要不要找父栏目
if($v['parent'] > 0){
$tree = array_merge($tree,familyTree($arr,$v['parent']));
}
//将此处移下来,可以实现顶级到次级效果。
$tree[] = $v;
}
}
return $tree;
}
print_r(familyTree($area,3));
总结:无限极分类的三个运用
1:指定栏目的子栏目
2::查找子孙树
3:查找家谱树
6、迭代查找家谱树。迭代在效率上比递归高。因此在查找家谱树的时候推荐使用迭代
function tree($arr,$id){
$tree = array();
while($id !== 0 ){
foreach($arr as $v){
if($v['id'] == $id){
$tree[] = $v;
$id = $v['parent'];
}
}
}
return $tree;
}
print_r(tree($area,8));
迭代查找子孙树
//迭代查找子孙树
function tree($arr,$parent = 0){
$task = array($parent);//任务表
$tree = array();//地区表
while(!empty($task)){
$flag =false;//用户判断是否找到子孙
foreach($arr as $k=>$v){
if($v['parent'] == $parent){//找到子孙
$tree[] = $v;
array_push($task,$v['id']);//放下目前任务,添加新任务
$parent = $v['id'];
unset($arr[$k]);//把已经找到的单元unset
$flag = true;//说明找到子栏目
}
}
if($flag == false){
array_pop($task);
$parent = end($task);
}
}
return $tree;
}
print_r(tree($area,0));