特色 :Library sort优于传统的插入排序(时间复杂度为O(n^2)),它的时间复杂度为O(nlogn),采用了空间换时间的策略。
思想 :一个图书管理员需要按照字母顺序放置书本,当在书本之间留有一定空隙时,一本新书上架将无需移动随后的书本,可以直接插空隙。Library sort的思想就源于此。

实现:有n个元素待排序,这些元素被插入到拥有(1+e)n个元素的数组中。每次插入2^(i-1)个元素,总共需要插logn趟。这2^(i-1)个元 素将被折半插入到已有的2^(i-1)个元素中。因此,插入i趟之后,已有2^i个元素插入数组中。此时,执行rebalance操作,原有处在(1+ e)2^i个位置的元素将被扩展到(2+2e)2^i个位置。这样,在做插入时,由于存在gap,因此在gap未满之前无需移动元素。

最好时间复杂度  O(nlogn)
平均时间复杂度  O(nlogn)
最坏时间复杂度  O(n^2)
空间复杂度    O(n)
是否稳定     是

  Library Sort基于折半查找的插入排序,插入时在元素附近空出一定位置,这样推入后移动元素的复杂度由原来的O(n)下降为平均O(1),于是整个算法的复杂度达到O(nlogn)。当输入正序或倒序时,插入点都在同一位置,“留空位”的策略失效,这时就出现最坏复杂度O(n^2)。

/*
* length:待排序元素个数
* elements:待排序数组
* factor:常数因子
*/
void librarySort(int length,float factor,int elements[]){
int i,j;
//扩展后的数组长度
int expandedLen = (int)((1+factor)*length);
int* orderedElem = (int*) malloc(expandedLen*sizeof(int));
//标志gap
int flag = 1<<31;
for(i=0;i<expandedLen;i++){
orderedElem[i] = flag;
}
int index = 1;
int numOfIntercalatedElem = 1;
orderedElem[0] = elements[0];
while(length>numOfIntercalatedElem){
//第i次插入2^(i-1)个元素
for(j=0;j<numOfIntercalatedElem;j++){
//待插入元素为elements[index]
//------------折半插入---------------
int mid;
int low = 0;
int high = 2 * numOfIntercalatedElem - 1;
while(low <= high){
mid = (low + high)/2;
int savedMid = mid;
//如果mid所在位置为gap
while(orderedElem[mid] == flag){
if(mid == high){
//当向右遍历没有找到元素值时,改成向左遍历
mid = savedMid - 1;
while(orderedElem[mid] == flag){
mid--;
}
break;
}
mid++;
}
if(elements[index] > orderedElem[mid]){
low = mid + 1;
//缩小范围
while(orderedElem[low] == flag){
low = low+1;
}
}else{
high = mid - 1;
}
}
//把elements[index]插入到orderedElem[high+1]
//当位置为空,没有存储元素值时...
if(orderedElem[high+1] == flag){
orderedElem[high+1] = elements[index];
}else{
//位置非空,首先往前挪动元素,如果前面已满,向后挪动元素
int temp = high+1;
while(orderedElem[temp] != flag){
temp--;
if(temp < 0){
temp = high+1;
break;
}
}
//向后移动
while(orderedElem[temp] !=flag){
temp++;
}
while(temp < high){
orderedElem[temp] = orderedElem[temp+1];
temp++;
}
while(temp > high+1){
orderedElem[temp] = orderedElem[temp-1];
temp--;
}
orderedElem[temp] = elements[index];
}
//---------------------------------
index++;
if(index == length){
break;
}
}
numOfIntercalatedElem *=2;
int generatedIndex;
//Rebalance...
for(j=numOfIntercalatedElem;j>0;j--){
if(orderedElem[j] == flag){
continue;
}
//原数组元素从i处移到2i处
generatedIndex = j*2;
if(generatedIndex >= expandedLen){
generatedIndex = expandedLen - 1;
if(orderedElem[generatedIndex] != flag){
break;
}
}
orderedElem[generatedIndex] = orderedElem[j];
orderedElem[j] = flag;
}
}
//测试输出
for(i=0;i<expandedLen;i++){
printf("%d\n",orderedElem[i]);
}
}

library sort (图书馆排序)相关推荐

  1. C++library Sort库排序的实现算法(附完整源码)

    C++library Sort库排序的实现算法 C++library Sort库排序的实现算法完整源码(定义,实现,main函数测试) C++library Sort库排序的实现算法完整源码(定义,实 ...

  2. library sort(图书馆排序)

    特色 :Library sort优于传统的插入排序(时间复杂度为O(n^2)),它的时间复杂度为O(nlogn),采用了空间换时间的策略. 思想 :一个图书管理员需要按照字母顺序放置书本,当在书本之间 ...

  3. redis 的使用 (sort set排序集合类型操作)

    sort set排序集合类型 释义: sort set 是 string 类型的集合 sort set 的每个元素 都会关联一个 权 通过 权值 可以有序的获取集合中的元素 应用场合: 获取热门帖子( ...

  4. Shell Sort 希尔排序 收藏

    Shell Sort 希尔排序 收藏 希尔排序(Shell Sort)又叫做缩小增量排序(diminishing increment sort),是一种很优秀的排序法,算法本身不难理解,也很容易实现, ...

  5. [Java基础] sort方法--------排序的那些事

    引言 在学习Java过程中,排序sort是我们常用的功能:在Java里,数组有Arrays.sort()可以排序,集合则是Collections.sort()方法排序:默认情况下是升序排列,但是降序又 ...

  6. Hark的数据结构与算法练习之图书馆排序

    算法说明 图书馆排序是插入排序的变种,典型的以空间换时间的一种方法.我个人感觉这种思路可以学习借鉴,但直接使用的场景应该不大. 我们知道,真正的插入排序通常往前边插入元素后,我们要把后边所有的元素后移 ...

  7. 关于SAP的“Sort key 排序码”

    对一个SAP新手来说,科目主档.客户主档.供应商主档中都有一个排序码栏位是比较不好理解的,下面我用图片来简单说明一下Sort key 排序码 的用途. 排序码的作用是凭证在生成时自动指定"分 ...

  8. 倒序排序_排序算法(六):Counting Sort 计数排序

    之前文章介绍的一些排序算法都是基于比较来进行排序的,故它们在平均情况下的时间复杂度最好也不过是线性对数级别.这里我们来介绍一种简单的基于非比较的排序算法--Counting Sort 计数排序,其时间 ...

  9. C语言最简单的sleep sort睡眠排序实现(附完整源码)

    C语言最简单的sleep sort睡眠排序实现 C语言最简单的sleep sort睡眠排序实现完整源码(定义,实现,main函数测试) C语言最简单的sleep sort睡眠排序实现完整源码(定义,实 ...

最新文章

  1. XP局域网访问无权限、不能互相访问问题的完整解决方案
  2. VB无所不能之三:VB截获Windows消息的钩子
  3. Flutter - International 国际化,Localization 本地化, 使用Intl
  4. 003_Spring使用Slf4j和logback日志
  5. Java中六大时间类的使用和区别
  6. 云炬60s看世界20211125
  7. Python模块: 文件和目录os+shutil
  8. linux系统每月定时重启,linux系统定时重启.doc
  9. spring boot jar包替换报错之Unable to open nested entry 'BOOT-INF/lib/cache-api-0.4.jar'.
  10. Http与WWW服务精解
  11. Javascript的数组操作(笔记)
  12. 关于电脑安装多个版本JDK后使用时的切换
  13. css-div定位详解
  14. xp 远程桌面无法找到该计算机,XP系统中远程无法连接指定计算机的处理方法
  15. 开发者生态与双引擎:华为的雄心壮志!
  16. 最全的HTTP1.1状态码
  17. 决策支持系统 (Decision-making Support System, DSS) (人机智能系统)
  18. 简单快捷的ArcGIS 10.7安装方法
  19. jaxl php,php – jaxl无法连接到Prosody
  20. Merkle tree for non-membership proof

热门文章

  1. 解读 2018:13 家开源框架谁能统一流计算?
  2. python turtle画表情包
  3. 用python实现聚类分析
  4. upc组队训练第十九场
  5. mysql 中 一个汉字吗_MySQL 中一个汉字占多少存储?
  6. 【python柱状图】图例大小、位置,X轴刻度大小,旋转角度
  7. 云和恩墨校园猎手招募令
  8. 【模型分享】全网质量最高最全《王者荣耀》角色3D模型独立角色
  9. “2019年新出的境外云闪付是什么?
  10. 爬取网易云某歌曲所有评论,并输出词云图