快速排序及STL中的sort算法
快速排序基本思想是,对待排序序列进行划分(Partition),一次划分,选择一个元素作为枢轴,然后将所有比枢轴小的元素放到枢轴的左边,将比枢轴大的元素放到枢轴的右边。然后对该枢轴划分的左右子序列分别再进行划分,如此递归。Partition是一个非常重要的概念,因为它只需要O(n)的时间复杂度就可以将待排序序列划分为两块具有大小关系的区间,可以根据这一特性求解待排序序列中最大的k个数、第k大的数等类似问题。
快速排序算法复杂度O(nlogn).
就平均时间而言,快速排序是目前被认为是最好的一种内部排序方法,其平均时间是O(nlogn),最坏情况是O(n^2),最坏的情况就是如下倒序完后再正序排的情况。
C++代码如下:
#include "stdafx.h" #define MAXSIZE 20 typedef struct{
int r[MAXSIZE+];
int len;
}SqList; int Partition(SqList &L, int low, int high)
{
L.r[] = L.r[low]; // 以第一个元素作为枢轴
int pivotkey = L.r[low];// 记录枢轴关键字
while (low < high)
{
while(low<high && L.r[high]>=pivotkey)
--high;// 找到从high位置开始向前第一个比枢轴小的元素
L.r[low] = L.r[high];// 将找到的比枢轴小的元素放到前边的空闲位置
while(low<high && L.r[low]<=pivotkey)
++low;// 找到从low位置开始向后第一个比枢轴大的元素
L.r[high] = L.r[low];// 将找到的比枢轴大的元素放到后边的空闲位置
}
L.r[low] = L.r[];// 将枢轴放回中间的空闲位置,由while{}循环可知,low最后空闲 return low;
} void QSort(SqList &L, int low, int high)
{
if (low < high)
{
int pivotloc = Partition(L, low, high);
QSort(L, low, pivotloc-);
QSort(L, pivotloc+, high);
}
} int _tmain(int argc, _TCHAR* argv[])
{
SqList sqList;
for (int i=; i<MAXSIZE+; i++)
{
sqList.r[i] = MAXSIZE - i;
}
sqList.len = MAXSIZE; QSort(sqList, , sqList.len); return ;
}
// 附一次划分过程,第一行为index,第二行为待排序序列
// 0 1 2 3 4 5 6 7
// __ 49 38 65 97 76 13 27 // 开始时,0号位空闲(low:1, high:7)
// 49 __ 38 65 97 76 13 27 // 将第1号元素作为枢轴,放到0号位,1号位冗余(low:1, high:7)
// 49 27 38 65 97 76 13 __ // 发现27比49小,将7号位值放到1号位,7号位冗余(low:1, high:7)
// 49 27 38 __ 97 76 13 65 // 发现65比49大,将3号位值放到7号位,3号位冗余(low:3, high:7)
// 49 27 38 13 97 76 __ 65 // 发现13比49小,将6号位值放到3号位,6号位冗余(low:3, high:6)
// 49 27 38 13 __ 76 97 65 // 发现97比49大,将4号位值放到6号位,4号位冗余(low:4, high:5)
// __ 27 38 13 49 76 97 65 // low == high,将枢轴放到4号位,此时49左边的都比49小,右边的都比49大
STL的所有关系型容器都拥有自动排序的功能(底层采用RB-tree),所以不需要sort算法。序列式容器的中的stack、queue等都有特别的出入口,不允许用户对元素进行排序。剩下的vector、deque和list,前两者的迭代器属于RandomAccessIterators,适合sort算法。泛型算法一定要求迭代器是RandomAccessIterators。因为任何一个元素都可以被选作枢轴(pivot),但是其合适与否却会影响Quick Sort的效率。为了避免枢轴不够随机带来的恶化效应,最理想的方式是取整个序列的头、尾、中央三个位置的元素,以其中值作为枢轴,这种做法成为三点中值(Median-of-Three),为了能够快速取出中央位置的元素,显然迭代器必须能够随机定位,因此快速排序的泛型算法中迭代器必须是RandomAccessIterators。
STL的sort算法,数据量大时采用Quick Sort,分段递归排序。一旦分段后的数据量小于某个门槛,为避免Quick Sort的递归调用带来过大的额外负担,就改用Insertion Sort。Insertion Sort虽然时间复杂度是O(n^2),但是当数据量很小时,却有不错的效果。另外虽然STL有三点中值来防止枢轴选取不当的问题,还有introsort进行自我侦测,如果分割行为有恶化倾向时,会转而改用Heap Sort。
快速排序及STL中的sort算法的更多相关文章
- STL中的排序算法
本文转自:STL中的排序算法 1. 所有STL sort算法函数的名字列表: 函数名 功能描述 sort 对给定区间所有元素进行排序 stable_sort 对给定区间所有元素进行稳定排序 ...
- STL中的所有算法(70个)
STL中的所有算法(70个)----9种类型(略有修改by crazyhacking) 参考自: http://www.cppblog.com/mzty/archive/2007/03/14/1981 ...
- 为什么map对象不能使用stl中的sort函数
STL所提供的各式各样算法中,sort()是最复杂最庞大的一个.这个算法接受两个RandomAccestlerators(随机存取迭代器),然后将区间内的所有元素以渐增方式由小到大重新排列.第二个版本 ...
- STL中的查找算法
STL中有很多算法,这些算法可以用到一个或多个STL容器(因为STL的一个设计思想是将算法和容器进行分离),也可以用到非容器序列比如数组中.众多算法中,查找算法是应用最为普遍的一类. 单个元素查找 1 ...
- STL中主要的算法(一)
一.replace() 替换算法将指定元素值替换为新值,使用原型例如以下,将迭代器[first,last)中值为old_value的元素所有替换为new_value值. 函数原型: template ...
- 【决战西二旗】|理解Sort算法
前言 前面两篇文章介绍了快速排序的基础知识和优化方向,今天来看一下STL中的sort算法的底层实现和代码技巧. 众所周知STL是借助于模板化来支撑数据结构和算法的通用化,通用化对于C++使用者来说已经 ...
- STL中的算法
STL中的所有算法(70个) 参考自:http://www.cppblog.com/mzty/archive/2007/03/14/19819.htmlhttp://hi.baidu.com/ding ...
- STL中vector的赋值,遍历,查找,删除,自定义排序——sort,push_back,find,erase
今天学习网络编程,那个程序中利用了STL中的sort,push_back,erase,自己没有接触过,今天学习一下,写了一个简单的学习程序.编译环境是VC6.0 这个程序使用了vect ...
- STL中sort、priority_queue、map、set的自定义比较函数
STL中,sort的默认排序为less,也就是说从小到大排序:priority_queue默认是less,也就说大顶堆:map默认是less,也就说用迭代器迭代的时候默认是小的排在前面:set默认是l ...
随机推荐
- 解决WCF跨机器调用时发生“调用方未由服务进行身份验证”的错误
1.服务器端Web.config配置文件,增加如下部分: <system.serviceModel> <bindings> <wsHttpBinding> < ...
- 自定义select 小三角
把select小三角换成自己的图片 效果: css样式: <style> #my_select { display: flex; display: -webkit-flex; width: ...
- css实现修改默认滚动条样式
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN"><html><head&g ...
- JDBC中常用对象介绍
JDBC中的主要类(接口) 在JDBC中常用的类有: 1.DriverManager 2.Connection 3.Statement 4.ResultSet 1.DriverManager 其实我们 ...
- 本地调试 谷歌浏览器报错:跨域问题处理 Access-Control-Allow-Origin
前端在本地,调试,就经常的就是会遇到 调用接口,提示跨域了. 如你要访问 http://****/api/user chrome 浏览器 报错: XMLHttpRequest cannot load ...
- Search Insert Position 查找给定元素在数组中的位置,若没有则返回应该在的位置
Given a sorted array and a target value, return the index if the target is found. If not, return the ...
- Python爬虫教程-00-写在前面
鉴于好多人想学Python爬虫,缺没有简单易学的教程,我将在CSDN和大家分享Python爬虫的学习笔记,不定期更新 基础要求 Python 基础知识 Python 的基础知识,大家可以去菜鸟教程进行 ...
- leetcode Ch6-Data Structure
1. Sliding Window Maximum class Solution { public: vector<int> maxSlidingWindow(vector<int& ...
- 关于webWorker的理解和简单例子
一.理解 当在 HTML 页面中执行脚本时,页面的状态是不可响应的,直到脚本已完成. web worker 是运行在后台的 JavaScript,独立于其他脚本,不会影响页面的性能.您可以继续做任何愿 ...
- maven dependendency
登录|注册 zhengsj的专栏 目录视图 摘要视图 订阅 [公告]博客系统优化升级 [收藏]Html5 精品资源汇集 博乐招募开始啦 Maven De ...