如有$array=$array(2001,2002,2003,2007,2008,2009,2010,2011,3015,4052,4053,4054)表示成200[1-2]|200[7-9]|201[0-1]|3015|405[2-4]
要求:1、$array中元素是任意多个,每个元素可以是任意数字但不重复
2、输出结果要符合正则表达式
3、要考虑周全。例如单个不连续数字的处理,数组只有一个元素的情况
新手求助求助
要求:1、$array中元素是任意多个,每个元素可以是任意数字但不重复
2、输出结果要符合正则表达式
3、要考虑周全。例如单个不连续数字的处理,数组只有一个元素的情况
新手求助求助
for($i=1; $i<count($ar); $i++) {
$v = $ar[$i];
if($v == $last+1 && substr($v, -1) > substr($last, -1)) {
$last = $v;
$min = min($min, $last);
}else {
if($last == $min)
$r[] = $last;
else
$r[] = sprintf("%s[%s-%s]", substr($min, 0, -1), substr($min, -1), substr($last, -1));
$last = $min = $v;
}
}
if($last != $min) {
$r[] = sprintf("%s[%s-%s]", substr($min, 0, -1), substr($min, -1), substr($last, -1));
}
echo join('|', $r);
200[1-3]|200[7-9]|201[0-1]|3015|405[2-4]
//我也来一个。。
$array=array(2001,2002,2003,2007,2008,2009,2010,2011,3015,4052,4053,4054);
$rs = array();
$keys = array();
for($i=1; $i<count($array); $i++) {
if($array[$i-1]+1 != $array[$i]) {
$keys[] = $i;
}
}
$rs = array();
$keys[] = count($array);
for($i=0; $i<count($keys); $i++) {
$startKey = $i-1 < 0 ? 0 : $i-1;
$startValue = $i-1 >= 0 ? $keys[$startKey] : 0;
$tmp = array_slice($array, $startValue, $keys[$i]-$startValue);
if(count($tmp)>1) {
$headLen = strlen($tmp[0]) - strlen(count($tmp));
$head = substr($tmp[0], 0, $headLen);
$foot = '['.substr($tmp[0], $headLen) . '-' . substr(end($tmp), $headLen) . ']';
$rs[] = $head . $foot;
}
else {
$rs[] = $tmp[0];
}
}
echo implode('|', $rs);
/**
输出结果:
200[1-3]|200[7-1]|3015|405[2-4]
*/
版主:200[1-3]|200[7-9]|201[0-1]|3015|405[2-4]|999[8-9]|1000[0-1]
我的:200[1-3]|200[7-1]|3015|405[2-4]|999[8-01]哈哈。。继续优化。。
而我的,肯定错了,呵呵。重新优化一下,跨位数的,也按一个区间显示。$array=array(2001,2002,2003,2007,2008,2009,2010,2011,3015,4052,4053,4054, 9998, 9999, 10000, 10001);
$rs = array();
$keys = array();
for($i=1; $i<count($array); $i++) { //将不连续的数的key记录
if($array[$i-1]+1 != $array[$i]) {
$keys[] = $i;
}
}
$rs = array();
$keys[] = count($array);
for($i=0; $i<count($keys); $i++) {
$startKey = $i-1 < 0 ? 0 : $i-1;
$startValue = $i-1 >= 0 ? $keys[$startKey] : 0;
$tmp = array_slice($array, $startValue, $keys[$i]-$startValue); //从上面记录的key,截取不同长度
if(strlen($tmp[0]) != strlen(end($tmp))) {
$rs[] = '[' . $tmp[0] . '-' . end($tmp) . ']'; //不同位数
}
elseif(count($tmp)>1) { //位数相同
$headLen = strlen($tmp[0]) - strlen(count($tmp));//计算相同的位数
$rs[] = substr($tmp[0], 0, $headLen) . '['.substr($tmp[0], $headLen) . '-' . substr(end($tmp), $headLen) . ']';
}
else { //单独一个数
$rs[] = $tmp[0];
}}
echo implode('|', $rs);
/**
输出结果:
200[1-3]|200[7-1]|3015|405[2-4]|[9998-10001]
*/
$arr_v = array_map(create_function('$v', 'return substr($v,-1);'), $arr);$pattern = '';
$time = 0;
for ($i = 1; $i <= count($arr_k); $i++){
if ($arr_k[$i] == $arr_k[$i-1]){//值与前一个相等
if ($arr_v[$i] == $arr_v[$i-1] + 1 ){//键连续,记录连续次数
$time++;
}
else{
$pattern .= sprintf('%d[%d-%d]|',$arr_k[$i],$arr_v[$i-1-$time],$arr_v[$i-1],$time);
$time = 0;
}
}
elseif ($time != 0) {//不相等,但有累加记录
$pattern .= sprintf('%d[%d-%d]|',$arr_k[$i-1],$arr_v[$i-1-$time],$arr_v[$i-1]);
$time = 0;
}
else {
$pattern .= sprintf('%d|',$arr_k[$i-1].$arr_v[$i-1]);
}
}echo $pattern;
$ar = array(2001,2002,2003,2007,2008,2009,2010,2011,3015,4052,4053,4054);
$i = 0;
foreach($ar as $v) {
$k = substr($v, 0, -1);
$v = substr($v, -1);
if(! isset($r[$k])) $i = 0;
if(isset($r[$k][$i]) && $v != max($r[$k][$i])+1) $i++;
$r[$k][$i][] = $v;
}foreach($r as $k=>$t)
foreach($t as $v)
if(count($v) == 1) $o[] = $k . $v[0];
else $o[] = sprintf('%s[%s-%s]', $k, min($v), max($v));echo join('|', $o);
8032-9110=>803[2-9]|80[4-9][0-9]|8[1-9][0-9][0-9]|90[0-9][0-9]|910[0-9]|9110 8102-8321=>810[2-9]|81[1-9][0-9]|82[0-9][0-9]|83[0-1][0-9]|832[0-1] 8000-8100=>80[0-9][0-9]|8100 8000-8099=>80[0-9][0-9] 8000-9999=>[8-9][0-9][0-9][0-9] 8000-8088=>80[0-7][0-9]|808[0-8]
6079-6088=>6079|608[0-8]
怎么做?
<?php
$arr = array(2001,2002,2003,2004,2005,2007,2008,2009,2010,2011,3015,4052,4053,4054);
function foobar($arr , $start =0, $flag=true){
if($start > count($arr)-1)return;
if((($arr[$start+1] - $arr[$start])== 1)&&((substr($arr[$start+1] , -1 ) - substr($arr[$start] , -1 )) == 1 )){
$str = ($flag ? ($start > 0 ? "|" :"") . substr($arr[$start] , 0,(strlen($arr[$start])-1))."[" : "")."|".substr($arr[$start] ,(strlen($arr[$start])-1),1);
$flag = false;
}else{
$new_flag = (($arr[$start] - $arr[$start-1])== 1)&&((substr($arr[$start] , -1 ) - substr($arr[$start-1] , -1 )) == 1 );
$me = substr($arr[$start] ,(strlen($arr[$start])-1),1);
$str = $flag ? "|".$arr[$start]:( $new_flag ? $str = "|".$me."]" : $str = "]|".$me);
$flag = true;
}
$eco .=$str.foobar($arr , $start+1 , $flag);
return $eco ;
}echo foobar($arr);
?>
$arr = array(2001,2002,2003,2004,2005,2007,2008,2009,2010,2011,3015,4052,4053,4054);
function foobar($arr , $start =0, $flag=true){
if($start > count($arr)-1)return;
if((($arr[$start+1] - $arr[$start])== 1)&&((substr($arr[$start+1] , -1 ) - substr($arr[$start] , -1 )) == 1 )){
$str = ($flag ? ($start > 0 ? "|" :"") . substr($arr[$start] , 0,(strlen($arr[$start])-1))."[" : "").($flag ? substr($arr[$start] ,(strlen($arr[$start])-1),1) :"");
$flag = false;
}else{
$new_flag = (($arr[$start] - $arr[$start-1])== 1)&&((substr($arr[$start] , -1 ) - substr($arr[$start-1] , -1 )) == 1 );
$me = substr($arr[$start] ,(strlen($arr[$start])-1),1);
$str = $flag ? "|".$arr[$start]:( $new_flag ? $str = "-".$me."]" : $str = "]|".$me);
$flag = true;
}
$eco .=$str.foobar($arr , $start+1 , $flag);
return $eco ;
}
echo foobar($arr);
?>
[8032-9110]
比
803[2-9]|80[4-9][0-9]|8[1-9][0-9][0-9]|90[0-9][0-9]|910[0-9]|9110
简洁得多,
而且前者的匹配效率也明显高于后者。
下面是我针对前者写的代码,不合楼主的要求,请便。
<?php$aCheckboxValue = array(1,2,3,4,200,400,2001,5600,2002,2003,2035,5601);//将数组从小到大排序
sort($aCheckboxValue);//获取数组长度
$length = count($aCheckboxValue);
$i = 0;
$pattern = '';//通过循环处理数组
while ($i < $length) {
$i ++;
//循环判断之后的数组元素是否连续
for ($j = $i; $j < $length; $j ++) {
if ($aCheckboxValue[$j] - $aCheckboxValue[$j - 1] != 1) {
//若不连续则跳出循环
break;
} else {
//若连续则继续判断下一个元素
continue;
}
}
if ($j - $i > 0) {
//有连续的则以字符组形式作为一个可选项追加到$pattern后面
$pattern .= '['.$aCheckboxValue[$i - 1].'-'.$aCheckboxValue[$j - 1].']|';
} else {
//没有连续的则直接作为一个可选项追加到$pattern后面
$pattern .= $aCheckboxValue[$i - 1].'|';
}
//移动数组下标位置到当前
$i = $j;
}//取出$pattern收尾的|符号
$pattern = trim($pattern, '| ');echo $pattern;
?>
$min=8032;$max=9110;
$cha=strlen($max)-strlen($min);
for($i=0;$i<$cha;$i++){
$min="0".$min;
}
//找出$min于$max的相同部分$same,以及不同部分
$same="";
for($i=1;$i<strlen($min);$i++)
if (substr($min,0,-$i)==substr($max,0,-$i)){
$same=substr($min,0,-$i);$min=substr($min,-$i);$max=substr($max,-$i);break;
}
//找出左边及中间部分
$middle=null;
if(substr($max,0,1)-substr($min,0,1)>=2){
$middle=sprintf('[%s-%s]',substr($min,0,1)+1,substr($max,0,1)-1);
}
for($i=1;$i<strlen($min);$i++){
$o=null;
if(substr($min,-$i,1)<9) {
if($i==1){
$o=sprintf('%s[%s-%s]',substr($min,0,-$i),substr($min,-$i,1),9);
//echo $o."<br>";
}else{
$o=sprintf('%s[%s-%s]',substr($min,0,-$i),substr($min,-$i,1)+1,9);
}
//echo $o."<br>";
}else{
if($i==1){
$o=sprintf('%s',$min);
}else{
}
}
if($o!=null){
for($j=1;$j<$i;$j++){
$o=$o."["."0"."-"."9"."]";
}
$o=preg_replace('/^0+/si','',$o);//去掉前边的0
$d[]=$o;
}
if($middle!=null)$middle=$middle."["."0"."-"."9"."]";
}
if($middle!=null)$d[]=$middle;
//echo $middle."<br>";
//找出右边部分.合并最后结果保存至$result
for($i=1;$i<strlen($max);$i++){
$k=null;
if(substr($max,$i,1)>0){
if($i==strlen($max)-1){
$k=sprintf('%s[%s-%s]',substr($max,0,$i),0,substr($max,$i,1));
}else{
$k=sprintf('%s[%s-%s]',substr($max,0,$i),0,substr($max,$i,1)-1);
}
}else{
if($i==strlen($max)-1){
$k=sprintf('%s',$max);
}else{
}
}
if($k!=null){
for($j=1;$j<strlen($max)-$i;$j++){
//echo $k."<br />";
$k=$k."["."0"."-"."9"."]";
}
$d[]=$k;
}
//$k="";
$result=join("|",$d);
}
echo $result."<br>";
/*sort($array);
$min=current($array);$max=end($array);if(strlen($max)==1&&$max!=$min){
$result="[$min-$max]";
return $result;
}elseif($max=$min&&strlen($max)==1){
$result=$min;
return $result;
}*/
$cha=strlen($max)-strlen($min);
for($i=0;$i<$cha;$i++){
$min="0".$min;
}
//找出$min于$max的相同部分$same,以及不同部分
$same=null;
for($i=1;$i<strlen($min);$i++)
if (substr($min,0,-$i)==substr($max,0,-$i)){
$same1=substr($min,0,-$i);$min=substr($min,-$i);$max=substr($max,-$i);$same=$same1;break;
}
//$min="$min";$max="$max";
//分类处理
if(strlen($max)==1){
$result="[$min-$max]";
}else{
//$same=$same1;
//找出左边及中间部分
$middle=null;
if(substr($max,0,1)-substr($min,0,1)>=2){
$middle=sprintf('[%s-%s]',substr($min,0,1)+1,substr($max,0,1)-1);
}
for($i=1;$i<strlen($min);$i++){
$o=null;
if(substr($min,-$i,1)<9) {
if($i==1){
$o=sprintf('%s[%s-%s]',substr($min,0,-$i),substr($min,-$i,1),9);
}else{
$o=sprintf('%s[%s-%s]',substr($min,0,-$i),substr($min,-$i,1)+1,9);
}
}else{
if($i==1){
$o=sprintf('%s',$min);
}else{
}
}
if($o!=null){
for($j=1;$j<$i;$j++){
$o=$o."["."0"."-"."9"."]";
}
if(!$same) $o=preg_replace('/^0+/','',$o);//去掉开始的0
$d[]=$o;
}
$left=join("|",$d);
if($middle!=null)$middle=$middle."["."0"."-"."9"."]";
}
if($middle!=null)$d[]=$middle;
//找出右边部分.合并最后结果保存至$result
for($i=1;$i<strlen($max);$i++){
$k=null;
if(substr($max,$i,1)>0){
if($i==strlen($max)-1){
$k=sprintf('%s[%s-%s]',substr($max,0,$i),0,substr($max,$i,1));
}else{
$k=sprintf('%s[%s-%s]',substr($max,0,$i),0,substr($max,$i,1)-1);
}
}else{
if($i==strlen($max)-1){
$k=sprintf('%s',$max);
}else{
}
}
//加上[0-9]
if($k!=null){
for($j=1;$j<strlen($max)-$i;$j++){
$k=$k."["."0"."-"."9"."]";
}
$d[]=$k;
}
$result=join("|",$d);
}
}
//去掉形如[0-0]的部分,用单个数字代替
for($i=0;$i<=9;$i++){
$result=str_replace("[$i-$i]","$i",$result);
}
$_array=explode("|",$result);//用“|”分解
//与相同部分组合
foreach ($_array as $key=>$value){
$value="$same".$value;
$_array[$key]=$value;
}
$result=join("|",$_array);//用‘|’分解
return $result;
}
function createarray($min=null,$max=null){
for($min;$min<$max+1;$min++){
$newarray[]=$min;
}
return $newarray;
}
//改为正则表达式
function num_change ($arr=array()){
sort($arr);
$min=current($arr);$max=end($arr); if(strlen($max)==1){
$result="[$min-$max]";
}else{
$result=change_rule($min,$max);
} for($i=0;$i<=9;$i++){
$result=str_replace("[$i-$i]","$i",$result);
}
return $result;
}//分解数组为二维数组
function array_change($originalarray=array()){
sort($originalarray);
$son_array=array();
foreach ($originalarray as $value){
if(!$son_array||$son_array[count($son_array)-1]==$value-1){
$son_array[]=$value;
}else{
$final_array[]=$son_array;
$son_array=array($value);
}
}
if($son_array) $final_array[]=$son_array;
return $final_array;
}function array_result($array=array()){
if(!$array) return;
$arr=array_change($array);
$a=array();
foreach($arr as $value){
$a[]=num_change($value);
//print_r($a);
}
$result=join('|',$a);
return $result;
}$arr=createarray(8032,9110);
echo array_result($arr);
?>