折半插入排序
只有比别人更早、更勤奋地努力,才能尝到成功的滋味。 ------麦克马斯特大学训言
记得之前总结过插入排序,有兴趣的可以看看---插入排序。
如果在最复杂的情况下,所要排序的整个数列是逆序的,当第 i-1 趟需要将 第 i 个元素插入前面的 0~ i -1 个元素的序列当中的时候,它总是会从第 i -1 个元素开始,逐个比较每个元素的大小,直到找到相应的位置。
这个算法中丝毫没有考虑当要插入第 i 个元素时前面的 0~~ i -1 序列是有序的这个特点。今天要总结的这个算法就充分的利用了这一点。
算法的基本过程:
1)计算 0 ~ i-1 的中间点,用 i 索引处的元素与中间值进行比较,如果 i 索引处的元素大,说明要插入的这个元素应该在中间值和刚加入i索引之间,反之,就是在刚开始的位置 到中间值的位置,这样很简单的完成了折半;
2)在相应的半个范围里面找插入的位置时,不断的用(1)步骤缩小范围,不停的折半,范围依次缩小为 1/2 1/4 1/8 .......快速的确定出第 i 个元素要插在什么地方;
3)确定位置之后,将整个序列后移,并将元素插入到相应位置。
算法实现:
import java.util.*; public class BinaryInsertSort { private static int[] Sort(int[] arr) { int i, j; //保存中间插入的值 int insertNote = 0; //将待排序的数列保存起来 int[] array = arr; System.out.println("开始排序:"); for (i = 1; i < array.length; i++) { int low = 0; int high = i - 1; insertNote = array[i]; //不断的折半 while (low <= high) { //找出中间值 int mid = (low + high) / 2; //如果大于中间值 if (array[i] > array[mid]) { //在大于中间值的那部分查找 low = mid+1; } else //在小于中间值的那部分查找 high = mid-1; } //将整体数组向后移 for ( j=i; j > low; j--) { array[j] = array[j - 1]; } //插入到指定的位置 array[low] = insertNote; System.out.println(Arrays.toString(array)); } System.out.println("排序之后:"); System.out.println(Arrays.toString(array)); return array; } public static void main(String[] args) { Random random = new Random(); int[] array = new int[10]; for (int i = 0; i < 10; i++) { array[i] = Math.abs(random.nextInt() % 100); } System.out.println("排序之前:"); System.out.println(Arrays.toString(array)); BinaryInsertSort.Sort(array); } }
输出截图:
算法分析:
1)时间复杂度:
折半插入排序比直接插入排序明显减少了关键字之间的比较次数,但是移动次数是没有改变。所以,折半插入排序和插入排序的时间复杂度相同都是O(N^2),在减少了比较次数方面它确实相当优秀,所以该算法仍然比直接插入排序好。
2)空间复杂度:
折半插入排序和插入排序一样只需要一个多余的缓存数据单元来放第 i 个元素,所以空间复杂度是O(1),因为排序前2个相等的数在序列的前后位置顺序和排序后它们两个的前后位置顺序相同,所以它是一个稳定排序。
作者:Orson
出处:http://www.cnblogs.com/java-class/
如果,您认为阅读这篇博客让您有些收获,不妨点击一下右下角的【推荐】
如果,您希望更容易地发现我的新博客,不妨点击一下左下角的【关注我】
如果,您对我的博客内容感兴趣,请继续关注我的后续博客,我是【Orson】
本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段
声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 分享 3 个 .NET 开源的文件压缩处理库,助力快速实现文件压缩解压功能!
· Ollama——大语言模型本地部署的极速利器
· DeepSeek如何颠覆传统软件测试?测试工程师会被淘汰吗?