PHP Shell 排序算法
最后修改于 2025 年 4 月 16 日
基本定义
算法 是一种逐步解决问题或执行计算的程序。在编程中,算法被实现为函数或方法。
排序 是指将数据按特定顺序排列,通常是升序或降序。有效的排序对于优化其他算法(如搜索操作)至关重要。
常见的排序算法包括
- 气泡排序
- 选择排序
- 插入排序
- 归并排序
- 快速排序
- 堆排序
- Shell Sort(希尔排序)
Shell 排序概述
Shell 排序是插入排序的一种优化,它允许交换相隔较远的项。它的工作原理是按特定的间隔对元素进行排序,然后减小间隔,直到间隔变为 1。
该算法由 Donald Shell 于 1959 年发明。它的时间复杂度根据使用的间隔序列而变化,通常在 O(n) 和 O(n²) 之间。
Shell 排序实现
这是一个 PHP 中对数字数据的 Shell 排序的基本实现
shell_sort.php
<?php function shellSort(array $arr): array { $n = count($arr); $gap = floor($n / 2); while ($gap > 0) { for ($i = $gap; $i < $n; $i++) { $temp = $arr[$i]; $j = $i; while ($j >= $gap && $arr[$j - $gap] > $temp) { $arr[$j] = $arr[$j - $gap]; $j -= $gap; } $arr[$j] = $temp; } $gap = floor($gap / 2); } return $arr; } $numbers = [12, 34, 54, 2, 3]; $sorted = shellSort($numbers); print_r($sorted);
此实现将数字按升序排序。间隔从数组长度的一半开始,每次迭代减半,直到达到 0。
对文本数据进行排序
Shell 排序也可以按字母顺序对字符串进行排序。 这是一个例子
shell_sort_strings.php
<?php function shellSortStrings(array $arr): array { $n = count($arr); $gap = floor($n / 2); while ($gap > 0) { for ($i = $gap; $i < $n; $i++) { $temp = $arr[$i]; $j = $i; while ($j >= $gap && strcmp($arr[$j - $gap], $temp) > 0) { $arr[$j] = $arr[$j - $gap]; $j -= $gap; } $arr[$j] = $temp; } $gap = floor($gap / 2); } return $arr; } $names = ["apple", "orange", "banana", "pear"]; $sortedNames = shellSortStrings($names); print_r($sortedNames);
此版本使用 strcmp
比较字符串。 它将数组按升序字母顺序排序。
降序排序
要按降序排序,我们只需反转比较条件
shell_sort_desc.php
<?php function shellSortDesc(array $arr): array { $n = count($arr); $gap = floor($n / 2); while ($gap > 0) { for ($i = $gap; $i < $n; $i++) { $temp = $arr[$i]; $j = $i; while ($j >= $gap && $arr[$j - $gap] < $temp) { $arr[$j] = $arr[$j - $gap]; $j -= $gap; } $arr[$j] = $temp; } $gap = floor($gap / 2); } return $arr; } $numbers = [12, 34, 54, 2, 3]; $sortedDesc = shellSortDesc($numbers); print_r($sortedDesc);
唯一的改变是将比较运算符从 >
更改为 <
。 这使得算法按降序排序。
Shell 排序 vs 快速排序
让我们将 Shell 排序与快速排序进行比较,快速排序是最快的排序算法之一。 我们将使用一个大型数组来对两者进行基准测试。
sort_benchmark.php
<?php function quickSort(array $arr): array { if (count($arr) <= 1) { return $arr; } $pivot = $arr[0]; $left = $right = []; for ($i = 1; $i < count($arr); $i++) { if ($arr[$i] < $pivot) { $left[] = $arr[$i]; } else { $right[] = $arr[$i]; } } return array_merge(quickSort($left), [$pivot], quickSort($right)); } // Generate large array $largeArray = range(1, 10000); shuffle($largeArray); // Shell Sort benchmark $start = microtime(true); shellSort($largeArray); $shellTime = microtime(true) - $start; // Quick Sort benchmark $start = microtime(true); quickSort($largeArray); $quickTime = microtime(true) - $start; echo "Shell Sort time: " . number_format($shellTime, 6) . " seconds\n"; echo "Quick Sort time: " . number_format($quickTime, 6) . " seconds\n";
在典型运行中,对于大型数据集,快速排序将比 Shell 排序更快。 但是,Shell 排序在处理中等大小的数组或内存受限时具有优势,因为它是一种就地排序算法。
何时使用 Shell 排序
- 中等大小的数组: Shell 排序在对于简单排序来说太大但又不太大的数组上表现良好。
- 内存限制: 作为一个就地算法,它使用最少的额外内存。
- 部分排序的数据: 当数据已经部分有序时,它可以很有效。
来源
本教程介绍了 PHP 中的 Shell 排序算法,并提供了数字和文本数据的示例,包括与快速排序的性能比较。
作者
列出 所有 PHP 教程。