PHP九大算法

5 篇文章 0 订阅
<?php

class Algorithm
{
    /**
     * @param $arr
     * @return mixed
     * 选择排序
     */
    function selectionSort($arr)
    {
        $len = count($arr);
        if ($len == 0 || !is_array($arr)) {
            return [];
        }
        for ($i = 0; $i < $len - 1; $i++) {
            $min_key = $i;
            for ($j = $i + 1; $j < $len; $j++) {
                if ($arr[$min_key] > $arr[$j]) {
                    $min_key = $j;
                }
            }
            if ($min_key != $i) {
                $tmp_val       = $arr[$min_key];
                $arr[$min_key] = $arr[$i];
                $arr[$i]       = $tmp_val;
            }
        }

        return $arr;
    }


    /**
     * @param $arr
     * @return array
     * 插入排序
     */
    function insertSort2($arr)
    {
        $len = count($arr);
        if ($len == 0 || !is_array($arr)) {
            return [];
        }
        for ($i = 0; $i < $len - 1; $i++) {
            for ($j = $i + 1; ($j >= 0) && ($arr[$j] < $arr[$j - 1]); $j--) {
                $tmp         = $arr[$j];
                $arr[$j]     = $arr[$j - 1];
                $arr[$j - 1] = $tmp;
            }
        }
        return $arr;
    }

    /**
     * @param $arr
     * @return array
     * 插入排序
     */
    function insertSort($arr)
    {
        $len = count($arr);
        if ($len == 0 || !is_array($arr)) {
            return [];
        }
        for ($i = 1; $i < $len; $i++) {
            $tmp_val = $arr[$i];
            for ($j = $i - 1; ($j >= 0) && ($tmp_val < $arr[$j]); $j--) {
                $arr[$j + 1] = $arr[$j];
                $arr[$j]     = $tmp_val;
            }
        }
        return $arr;
    }


    /**
     * @param $arr
     * 堆排序
     */
    //

    
	$array = [2,5,21,4,77,8,999,66];
	$array = adjustMaxHeap($array);
	$len = count($array);
	$length = $len;
	for ($i = 0; $i < $length; $i++) {
		$array = swap($array,0,$len-1);
		$len--;
		adjust($array, $len, 0);
	}
	print_r($array);



	function adjustMaxHeap($array) {
		$len = count($array);
		$lastParentNode = floor($len/2);
		for($i = $lastParentNode; $i>=0; $i--) {
			adjust($array, $len, $i);
		}
		return $array;
	}

	
	function adjust(&$array, $len, $i) {
		$left  = 2 * $i + 1;
		$right = 2 * $i + 2;
		$largest = $i;
		if (($left < $len) && ($array[$left] < $array[$largest])){
			$largest = $left;
		}
		if (($right < $len) && ($array[$right] < $array[$largest])){
			$largest = $right;
		}
		
		if ($i != $largest) {
			$array = swap($array, $largest, $i);
			adjust($array, $len, $largest);
		}
	}
	

	function swap($array, $a, $b) {
		$tmp = $array[$a];
		$array[$a] = $array[$b];
		$array[$b] = $tmp;
		return $array;
	}




    //

    /**
     * @param $arr
     * @return array
     * 冒泡排序
     */
    function bubbleSort($arr)
    {
        $len = count($arr);
        if ($len == 0 || !is_array($arr)) {
            return [];
        }
        for ($i = 0; $i < $len - 1; $i++) {
            for ($j = $len - 1; $j > $i; $j--) {
                if ($arr[$j] < $arr[$j - 1]) {
                    $tmp_val     = $arr[$j];
                    $arr[$j]     = $arr[$j - 1];
                    $arr[$j - 1] = $tmp_val;
                }
            }
        }
        return $arr;
    }

    //最好时间N 最差N
   function  bestPao($array)
{
	$len = count($array);
	if ($len > 0) {
		$is_swap = 0;
		for ($i = 0; $i < $len-1; $i++) {
			for ($j = 0; $j<$len-1; $j++) {
				if ($array[$j+1] < $array[$j]) {
					$is_swap = 1;
					$tmp = $array[$j+1];
					$array[$j+1] = $array[$j];
					$array[$j] = $tmp;
				}
			}
			if ($is_swap == 0) {
				return $array;
			}
		}
	}
	return $array;
}
	
    /**
     * @param $arr
     * @return array
     * 快速排序
     * 一定要注意边界值
     */
    function quickSort($arr)
    {
        $len = count($arr);
        if ($len <= 1 || !is_array($arr)) {
            return $arr;
        }
        $target = $arr[0];
        $right  = [];
        $left   = [];
        for ($i = 1; $i < $len; $i++) {
            if ($arr[$i] >= $target) {
                $right[] = $arr[$i];
            } else {
                $left[] = $arr[$i];
            }
        }
        $left    = $this->quickSort($left);
        $right   = $this->quickSort($right);
        $new_arr = array_merge($left, [$target], $right);
        return $new_arr;
    }


/
    /**
     * @param $arr
     * @return array
     * 二路归并排序
     * 关键字 分两路,排序,递归
     */
    function mergeSort($arr)
    {
        $len = count($arr);
        if ($len <= 1 || !is_array($arr)) {
            return $arr;
        }

        $slen  = intval($len / 2);
        $left  = array_slice($arr, 0, $slen);
        $right = array_slice($arr, $slen);
        return $this->merge($this->mergeSort($left), $this->mergeSort($right));
    }

    function merge($a, $b)
    {
        $len_a = count($a);
        $len_b = count($b);
        $ret   = [];
        $i     = 0;
        $j     = 0;
        while ($i < $len_a || $j < $len_b) {
            if (isset($a[$i]) && isset($b[$j])) {
                if ($a[$i] > $b[$j]) {
                    $ret[] = $b[$j];
                    $j++;
                } else {
                    $ret[] = $a[$i];
                    $i++;
                }
            } elseif (isset($a[$i])) {
                $ret[] = $a[$i];
                $i++;
            } elseif (isset($b[$j])) {
                $ret[] = $b[$j];
                $j++;
            }
        }
        return $ret;
    }


    /**
     * @param $arr
     * @return array
     * 桶排序
     */
    function bucketSort($arr)
    {
        $len = count($arr);
        if ($len <= 1 || !is_array($arr)) {
            return $arr;
        }
        $min_val = min($arr);
        $max_val = max($arr);
        $ret_array = array_fill($min_val, $max_val-$min_val+1, 0);
        foreach ($arr as $val) {
            $ret_array[$val]++;
        }
        $ret = [];
        foreach ($ret_array as $key=>$val) {
            while ($val > 0) {
                $ret[] = $key;
                $val--;
            }
        }
        return $ret;
    }


    /**
     * @param $arr
     * @return array
     * 基数排序
     */
    function radix($arr)
    {
        $len = count($arr);
        if ($len <= 1 || !is_array($arr)) {
            return $arr;
        }
        $max_val = max($arr);
        $radix_len = strlen($max_val);
        $mod_val = 10;
        $dev_val = 1;
        for ($i=1; $i<=$radix_len; $i++) {
            $arr = $this->radixOrder($arr, $mod_val, $dev_val);
            $dev_val *= 10;
        }
        return $arr;
    }

    function radixOrder($arr, $mod_val, $dev_val)
    {
        $ret_array = array_fill(0, 10, []);
        $len = count($arr);
        for ($i = 0; $i < $len; $i++) {
            $tmp_val = intval($arr[$i] / $dev_val) % $mod_val;
            $ret_array[$tmp_val][] = $arr[$i];
        }
        $ret = [];
        foreach ($ret_array as $key=>$val) {
            foreach ($val as $item) {
                $ret[] = $item;
            }
        }
        return $ret;
    }


    /**
     * @param $arr
     * 希尔排序
     */
    function shellSort($arr) {
        $len = count($arr);
        if ($len <= 1 || !is_array($arr)) {
            return $arr;
        }
        $inc = floor($len / 3) + 1;
        //$inc = intval($len / 2);
        for ($i = $inc; $i>0; $i = intval($i / 3)) {
            for ($j = 0; $j<$len; $j++) {
                $k = 0;
                while ($k < $len) {
                    if ((($k+$i) < $len) && ($arr[$k] > $arr[$k+$i])) {
                        $tmp_val = $arr[$k];
                        $arr[$k] = $arr[$k+$i];
                        $arr[$k+$i] = $tmp_val;
                    }
                    $k = $k+$i;
                }
            }
        }
        return $arr;
    }
}


//sort
$al  = new NewSale();
$arr = [33, 1, 44, 99, 66, 55, 44, 22, 77, 88, 11];
//选择排序;
//$ret = $al->selectionSort($arr);
//print_r($ret);
//插入排序
//$ret = $al->insertSort($arr);
//print_r($ret);
//堆排序
//$ret = $al->heapSort($arr);
//print_r($ret);
//冒泡排序
//$ret = $al->heapSort($arr);
//print_r($ret);
//快速排序
//$ret = $al->quickSort($arr);
//print_r($ret);
//$ret = $al->mergeSort($arr);
//print_r($ret);
//$ret = $al->bucketSort($arr);
//print_r($ret);
//$ret = $al->radix($arr);
//print_r($ret);

$ret = $al->shellSort($arr);
print_r($ret);

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
这里是用PHP写的几个基础算法算法的重要性貌似对于PHP程序员不怎么重要,其实是非常重要的,经典名句:算法+数据结构=程序。作为一名真正的高级PHP程序员,我认为应该熟悉C,如果你想成为真正的程序员,请好好学C,学好数据结构与算法。这里仅仅只是几个基础算法,还有很多东东要学…… 1、首先来画个菱形玩玩,很多人学C时在书上都画过,咱们用PHP画下,画了一半。 思路:多少行for一次,然后在里面空格和星号for一次。 <?phpfor($i=0;$i<=3;$i++){ for($j=0;$j<=3-$i;$j++){ echo ' '; } for($k=0;$k<=2*$i;$k++){ echo '*'; } echo '<br/>'; } 2、冒泡排序,C里基础算法,从小到大对一组数排序。 思路:这题从小到大,第一轮排最小,第二轮排第二小,第三轮排第三小,依次类推…… <?php$arr = array(3, 2, 1);$n = count($arr); //每循环一次,就跑一趟后面的排序for($j=0; $j<$n-1; $j++) {//对后面没排好的,循环查找出最大(最小)的,进行一趟排序 for($i=$j; $i<$n-1; $i++) { if($arr[$j] > $arr[$i+1]) { $t = $arr[$j]; $arr[$j] = $arr[$i+1]; $arr[$i+1] = $t; } }}print_r($arr); 3、杨辉三角,用PHP写。 思路:每一行的第一位和最后一位是1,没有变化,中间是前排一位与左边一排的和,这种算法是用一个二维数组保存,另外有种算法用一维数组也可以实现,一行一行的输出,有兴趣去写着玩下。 11 11 2 11 3 3 11 4 6 4 11 5 10 10 5 1 <?php//每行的第一个和最后一个都为1,写了6行 for($i=0; $i<6; $i++) { $a[$i][0]=1; $a[$i][$i]=1; } //出除了第一位和最后一位的值,保存在数组中 for($i=2; $i<6; $i++) { for($j=1; $j<$i; $j++) { $a[$i][$j] = $a[$i-1][$j-1]+$a[$i-1][$j]; } } //打印 for($i=0; $i<6; $i++){ for($j=0; $j<=$i; $j++) { echo $a[$i][$j].' '; } echo '<br/>'; } 4、在一组数中,要求插入一个数,按其原来顺序插入,维护原来排序方式。 思路:找到比要插入数大的那个位置,替换,然后把后面的数后移一位。 <?php$in = 2;$arr = array(1,1,1,3,5,7);$n = count($arr);//如果要插入的数已经最大,直接打印if($arr[$n-1] < $in) { $arr[$n+1] = $in; print_r($arr); } for($i=0; $i<$n; $i++) {//找出要插入的位置 if($arr[$i] >= $in){ $t1= $arr[$i]; $arr[$i] = $in;//把后面的数据后移一位 for($j=$i+1; $j<$n+1; $j++) { $t2 = $arr[$j]; $arr[$j] = $t1; $t1 = $t2; }//打印 print_r($arr); die; }} 5、对一组数进行排序(快速排序算法)。 思路:通过一趟排序分成两部分,然后递归对这两部分排序,最后合并。 <?phpfunction q($array) { if (count($array) <= 1) {return $array;}//以$key为界,分成两个子数组 $key = $array[0]; $l = array(); $r = array(); //分别进行递归排序,然后合成一个数组 for ($i=1; $i<count($array); $i++) { if ($array[$i] <= $key) { $l[] = $array[$i]; } else { $r[] = $array[$i]; } } $l = q($l); $r = q($r); return array_merge($l, array($key), $r);} $arr = array(1,2,44,3,4,33);print_r( q($arr) ); 6、在一个数组查找你所需元素(二分查找算法)。 思路:以数组中某个值为界,再递归进行查找,直到结束。 <?phpfunction find($array, $low, $high, $k){ if ($low <= $high){ $mid = intval(($low+$high)/2); if ($array[$mid] == $k){ return $mid; }elseif ($k < $array[$mid]){ return find($array, $low, $mid-1, $k); }else{ return find($array, $mid+1, $high, $k); } } die('Not have...');} //test$array = array(2,4,3,5);$n = count($array);$r = find($array,0,$n, 7、合并多个数组,不用array_merge(),题目来于论坛。 思路:遍历每个数组,重新组成一个新数组。 <?phpfunction t(){ $c = func_num_args()-1; $a = func_get_args(); //print_r($a); for($i=0; $i<=$c; $i++){ if(is_array($a[$i])){ for($j=0; $j<count($a[$i]); $j++){ $r[] = $a[$i][$j]; } } else { die('Not a array!'); } } return $r;} //testprint_r(t(range(1,4),range(1,4),range(1,4)));echo '<br/>';$a = array_merge(range(1,4),range(1,4),range(1,4));print_r($a); 8、牛年求牛:有一母牛,到4岁可生育,每年一头,所生均是一样的母牛,到15岁绝育,不再能生,20岁死亡,问n年后有多少头牛。(来自论坛) <?phpfunction t($n) { static $num = 1 for($j=1; $j<=$n; $j++){ if($j>=4 && $j<15) {$num++;t($n-$j);} if($j==20){$num--;} } return $num;} //testecho t(8); 这里是用PHP写的几个基础算法算法的重要性貌似对于PHP程序员不怎么重要,其实是非常重要的,经典名句:算法+数据结构=程序。作为一名真正的高级PHP程序员,我认为应该熟悉C,如果你想成为真正的程序员,请好好学C,学好数据结构与算法。这里仅仅只是几个基础算法,还有很多东东要学…… 1、首先来画个菱形玩玩,很多人学C时在书上都画过,咱们用PHP画下,画了一半。 思路:多少行for一次,然后在里面空格和星号for一次。 <?phpfor($i=0;$i<=3;$i++){ for($j=0;$j<=3-$i;$j++){ echo ' '; } for($k=0;$k<=2*$i;$k++){ echo '*'; } echo '<br/>'; } 2、冒泡排序,C里基础算法,从小到大对一组数排序。 思路:这题从小到大,第一轮排最小,第二轮排第二小,第三轮排第三小,依次类推…… <?php$arr = array(3, 2, 1);$n = count($arr); //每循环一次,就跑一趟后面的排序for($j=0; $j<$n-1; $j++) {//对后面没排好的,循环查找出最大(最小)的,进行一趟排序 for($i=$j; $i<$n-1; $i++) { if($arr[$j] > $arr[$i+1]) { $t = $arr[$j]; $arr[$j] = $arr[$i+1]; $arr[$i+1] = $t; } }}print_r($arr); 3、杨辉三角,用PHP写。 思路:每一行的第一位和最后一位是1,没有变化,中间是前排一位与左边一排的和,这种算法是用一个二维数组保存,另外有种算法用一维数组也可以实现,一行一行的输出,有兴趣去写着玩下。 11 11 2 11 3 3 11 4 6 4 11 5 10 10 5 1 <?php//每行的第一个和最后一个都为1,写了6行 for($i=0; $i<6; $i++) { $a[$i][0]=1; $a[$i][$i]=1; } //出除了第一位和最后一位的值,保存在数组中 for($i=2; $i<6; $i++) { for($j=1; $j<$i; $j++) { $a[$i][$j] = $a[$i-1][$j-1]+$a[$i-1][$j]; } } //打印 for($i=0; $i<6; $i++){ for($j=0; $j<=$i; $j++) { echo $a[$i][$j].' '; } echo '<br/>'; } 4、在一组数中,要求插入一个数,按其原来顺序插入,维护原来排序方式。 思路:找到比要插入数大的那个位置,替换,然后把后面的数后移一位。 <?php$in = 2;$arr = array(1,1,1,3,5,7);$n = count($arr);//如果要插入的数已经最大,直接打印if($arr[$n-1] < $in) { $arr[$n+1] = $in; print_r($arr); } for($i=0; $i<$n; $i++) {//找出要插入的位置 if($arr[$i] >= $in){ $t1= $arr[$i]; $arr[$i] = $in;//把后面的数据后移一位 for($j=$i+1; $j<$n+1; $j++) { $t2 = $arr[$j]; $arr[$j] = $t1; $t1 = $t2; }//打印 print_r($arr); die; }} 5、对一组数进行排序(快速排序算法)。 思路:通过一趟排序分成两部分,然后递归对这两部分排序,最后合并。 <?phpfunction q($array) { if (count($array) <= 1) {return $array;}//以$key为界,分成两个子数组 $key = $array[0]; $l = array(); $r = array(); //分别进行递归排序,然后合成一个数组 for ($i=1; $i<count($array); $i++) { if ($array[$i] <= $key) { $l[] = $array[$i]; } else { $r[] = $array[$i]; } } $l = q($l); $r = q($r); return array_merge($l, array($key), $r);} $arr = array(1,2,44,3,4,33);print_r( q($arr) ); 6、在一个数组查找你所需元素(二分查找算法)。 思路:以数组中某个值为界,再递归进行查找,直到结束。 <?phpfunction find($array, $low, $high, $k){ if ($low <= $high){ $mid = intval(($low+$high)/2); if ($array[$mid] == $k){ return $mid; }elseif ($k < $array[$mid]){ return find($array, $low, $mid-1, $k); }else{ return find($array, $mid+1, $high, $k); } } die('Not have...');} //test$array = array(2,4,3,5);$n = count($array);$r = find($array,0,$n, 7、合并多个数组,不用array_merge(),题目来于论坛。 思路:遍历每个数组,重新组成一个新数组。 <?phpfunction t(){ $c = func_num_args()-1; $a = func_get_args(); //print_r($a); for($i=0; $i<=$c; $i++){ if(is_array($a[$i])){ for($j=0; $j<count($a[$i]); $j++){ $r[] = $a[$i][$j]; } } else { die('Not a array!'); } } return $r;} //testprint_r(t(range(1,4),range(1,4),range(1,4)));echo '<br/>';$a = array_merge(range(1,4),range(1,4),range(1,4));print_r($a); 8、牛年求牛:有一母牛,到4岁可生育,每年一头,所生均是一样的母牛,到15岁绝育,不再能生,20岁死亡,问n年后有多少头牛。(来自论坛) <?phpfunction t($n) { static $num = 1 for($j=1; $j<=$n; $j++){ if($j>=4 && $j<15) {$num++;t($n-$j);} if($j==20){$num--;} } return $num;} //testecho t(8);

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值