排序算法

关于常见排序算法的稳定性分析和结论

落爺英雄遲暮 提交于 2020-03-26 02:57:20
这几天笔试了好几次了,连续碰到一个关于常见排序算法稳定性判别的问题,往往还是多选,对于我以及和我一样拿不准的同学可不是一个能轻易下结论的题目,当 然如果你笔试之前已经记住了数据结构书上哪些是稳定的,哪些不是稳定的,做起来应该可以轻松搞定。本文是针对老是记不住这个或者想真正明白到底为什么是稳 定或者不稳定的人准备的。 首先,排序算法的稳定性大家应该都知道,通俗地讲就是能保证排序前2个相等的数其在序列的前后位置顺序和排序后它们两个的前后位置顺序相同。在简单形式化一下,如果Ai = Aj, Ai原来在位置前,排序后Ai还是要在Aj位置前。 其次,说一下稳定性的好处。排序算法如果是稳定的,那么从一个键上排序,然后再从另一个键上排序,第一个键排序的结果可以为第二个键排序所用。基数排序就 是这样,先按低位排序,逐次按高位排序,低位相同的元素其顺序再高位也相同时是不会改变的。另外,如果排序算法稳定,对基于比较的排序算法而言,元素交换 的次数可能会少一些(个人感觉,没有证实)。 回到主题,现在分析一下常见的排序算法的稳定性,每个都给出简单的理由。 (1)冒泡排序 冒泡排序就是把小的元素往前调或者把大的元素往后调。比较是相邻的两个元素比较,交换也发生在这两个元素之间。所以,如果两个元素相等,我想你是不会再无 聊地把他们俩交换一下的;如果两个相等的元素没有相邻,那么即使通过前面的两两交换把两个相邻起来

排序算法 java实现

不问归期 提交于 2020-03-26 01:44:54
为了笔试,用了一下午准备了下各种排序算法的java实现。给大家提供个方便,把代码都贴出来,算法的具体过程以后再补。 冒泡排序 1 package sort; 2 3 public class BubbleSort { 4 public static void swap(int[] source,int x,int y){ 5 int temp=source[y]; 6 source[y]=source[x]; 7 source[x]=temp; 8 } 9 /* 10 * 每次将最大的气泡沉底,需要(n-1)趟扫描,每次扫描(n-i)次 11 * 复杂度O(n2) 12 * 稳定 13 */ 14 public static void sort(int[] source){ 15 for(int i=source.length-1;i>0;i--){ 16 for(int j=0;j<i;j++){ 17 if(source[j]>source[j+1]) 18 swap(source, j, j+1); 19 } 20 } 21 } 22 23 public static void main(String[] args) { 24 int[] source={9,3,6,2,1,8,4,5}; 25 sort(source); 26 for (int i = 0; i <

python排序算法实现:

ε祈祈猫儿з 提交于 2020-03-26 01:44:08
选择排序: def sel_sort(arr): i=0; length =len(arr) while i<length: j = i+1 min = arr[i] while j<length: if arr[j]<min: min = arr[j] arr[j] = arr[i] arr[i] = min j+=1 i+=1 return arr 插入排序: def insert_sort(arr): i =1 while i <=len(arr)-1: key = arr[i]; j =i -1 i +=1 while j >=0 and arr[j]>key: arr[j+1] = arr[j] j -=1 arr[j+1] = key return arr a = insert_sort([1,2,4,3]) print(a) 归并排序: #子问题程序(对两组已排序数组进行合并排序)最小子程序数组长度为2,即p=q时 #0<=p<=q<r<=len(a), def merge(arr,p,q,r): left = arr[p:q+1] right = arr[q+1:r+1] left.append(100000)#哨兵 right.append(100000) i=0;j=0; k=r+1; while p<k: if left[i]<=right[j]:#比较

排序算法原理及实现

醉酒当歌 提交于 2020-03-26 01:43:02
插入排序 1 public static void insertSort(Comparable[] array) 2 { 3 int j = 0; 4 5 for (int i = 1; i < array.length; i++) { 6 Comparable temp = array[i]; 7 8 for (j = i; j > 0 && (temp.compareTo(array[j - 1]) < 0); j--) { 9 array[j] = array[j - 1]; 10 } 11 array[j] = temp; 12 } 13 } 归并排序 1 public static void mergeSort(Comparable[] array) 2 { 3 Comparable[] copy = new Comparable[array.length]; 4 mergeSort(array, copy, 0, array.length - 1); 5 } 6 7 8 private static void mergeSort(Comparable[] array, Comparable[] temp, int left, int right) 9 { 10 if (left < right) { 11 int middle = (left + right) >> 1

冒泡排序

自作多情 提交于 2020-03-26 01:42:44
冒泡排序,是指计算机的一种排序方法,它的时间复杂度为O(n^2),虽然不及堆排序、快速排序的O(nlogn,底数为2),但是有两个优点:1.“编程复杂度”很低,很容易写出代码;2.具有稳定性,这里的稳定性是指原序列中相同元素的相对顺序仍然保持到排序后的序列,而堆排序、快速排序均不具有稳定性。不过,一路、二路归并排序、不平衡二叉树排序的速度均比冒泡排序快,且具有稳定性,但速度不及堆排序、快速排序。冒泡排序是经过n-1趟子排序完成的,第i趟子排序从第1个数至第n-i个数,若第i个数比后一个数大(则升序,小则降序)则交换两数  冒泡排序(BubbleSort)的基本概念是:依次比较相邻的两个数,将小数放在前面,大数放在后面。即在第一趟:首先比较第1个和第2个数,将小数放前,大数放后。然后比较第2个数和第3个数,将小数放前,大数放后,如此继续,直至比较最后两个数,将小数放前,大数放后。至此第一趟结束,将最大的数放到了最后。在第二趟:仍从第一对数开始比较(因为可能由于第2个数和第3个数的交换,使得第1个数不再小于第2个数),将小数放前,大数放后,一直比较到倒数第二个数(倒数第一的位置上已经是最大的),第二趟结束,在倒数第二的位置上得到一个新的最大数(其实在整个数列中是第二大的数)。如此下去,重复以上过程,直至最终完成排序。   由于在排序过程中总是小数往前放,大数往后放,相当于气泡往上升

常用排序算法的Python实现

社会主义新天地 提交于 2020-03-26 01:25:03
最近一段时间学习了python,发现python真是个强大,强大到和Matlab相媲美。为了熟悉python,将之前的各种排序算法用python实现了一下。 常用的时间复杂度为O(n^2)的排序算法有冒泡排序,插入排序和选择排序,时间复杂度为O(nlog2(n))的算法有快速排序,归并排序和堆排序, 这里的快速排序的初始比较值partition是随机给定的,在用python进行编写时能更清楚的理解整个排序算法的过程。 1 import random 2 def BubbleSort(num): 3 n=len(num) 4 for i in range(0,n): 5 for j in range(i,n): 6 if num[i]>=num[j]: 7 num[i],num[j]=num[j],num[i] 8 return num 9 def SelectSort(num): 10 for i in range(0,len(num)): 11 mindex=i 12 for j in range(i,len(num)): 13 if num[mindex]>num[j]: 14 mindex=j 15 num[mindex],num[i]=num[i],num[mindex] 16 return num 17 def InsertSort(num): 18 for i in

八大排序算法概述

元气小坏坏 提交于 2020-03-26 01:24:33
综上,得出结论: 选择排序、快速排序、希尔排序、堆排序不是稳定的排序算法,而冒泡排序、插入排序、归并排序和基数排序是稳定的排序算法 常见排序算法的稳定性 收藏 排序算法的稳定性:若待排序的序列中,存在多个具有相同关键字的记录,经过排序, 这些记录的相对次序保持不变,则称该算法是稳定的;若经排序后,记录的相对 次序发生了改变,则称该算法是不稳定的。 稳定性的好处:排序算法如果是稳定的,那么从一个键上排序,然后再从另一个键上排序,第一个键排序的结果可以为第二个键排序所用。基数排序就是这样,先按低位排序,逐次按高位排序,低位相同的元素其顺序再高位也相同时是不会改变的。另外,如果排序算法稳定,可以避免多余的比较; 回到主题,现在分析一下常见的排序算法的稳定性,每个都给出简单的理由。 (1)冒泡排序 冒泡排序就是把小的元素往前调或者把大的元素往后调。比较是相邻的两个元素比较,交换也发生在这两个元素之间。所以,如果两个元素相等,我想你是不会再无聊地把他们俩交换一下的;如果两个相等的元素没有相邻,那么即使通过前面的两两交换把两个相邻起来,这时候也不会交换,所以相同元素的前后顺序并没有改变,所以冒泡排序是一种稳定排序算法。 (2)选择排序 选择排序是给每个位置选择当前元素最小的,比如给第一个位置选择最小的,在剩余元素里面给第二个元素选择第二小的,依次类推,直到第n-1个元素,第n个元素不用选择了

排序算法

别说谁变了你拦得住时间么 提交于 2020-03-26 01:01:58
最近忙着复习找工作,熟悉了下排序算法,动手写了一下,发现有些问题的边界条件还是没有考虑清楚,不过好在调试成功。 不稳定排序:堆排序,快速排序,希尔排序;稳定排序:插入排序,冒泡排序,选择排序,归并排序,基数排序等。 插入排序算法代码: void InsertSort(int A[],int n) { for(int i=1;i<n;i++) { int key=A[i]; int j=i-1; while(j>=0 && A[j]>key) { A[j+1]=A[j]; j--; } A[j+1]=key; } } 冒泡排序代码: void BubbleSort(int data[],int n) { int flag=0; for(int i=0;i<n;i++) { flag=0; for(int j=n-1;j>i;j--) { if(data[j]<data[j-1]) { swap(data[j],data[j-1]); flag=1; } } if(flag==0) break; } 下面是堆排序代码: #include <iostream> using namespace std; //堆筛选函数 //已知H[start~end]中除了start之外均满足堆的定义 //本函数进行调整,使H[start~end]成为一个大顶堆 void HeapAdjust(int H

经典排序算法实现

和自甴很熟 提交于 2020-03-26 00:53:21
冒泡排序 选择排序 插入排序 快速排序 堆排序 希尔排序 归并排序 //java 版本 package com.leej.sort; public class SortAlgorithm { //冒泡排序, 稳定, On^2 public static void BubbleSort(int[] nums) { int n = nums.length; for (int step = 1; step < n; step++) { boolean changed = false; for (int j = 0; j < n - step; j++) { if (nums[j] > nums[j + 1]) { swap(nums, j, j + 1); changed = true; } } if (!changed) return; } } //选择排序, 不稳定 On^2 public static void SelectSort(int[] nums) { int n = nums.length; for (int i = 0; i < n - 1; i++) { int minIndex = i; for (int j = i + 1; j < n; j++) { if (nums[minIndex] > nums[j]) minIndex = j; } if

基本排序算法(冒泡,快排,插入,希尔,选择,归并)

人盡茶涼 提交于 2020-03-26 00:50:05
这篇文章仅仅为心中自证,不是算法教学,也不想误人子弟,谢谢各位。 第一章:一些感慨   我断断续续学习算法两年多了,这说起来是多么苦涩,是我笨嘛?一直不知道算法是什么东西。 从《算法导论》再到《C算法》不清楚看了多少遍,它们就是我过不去的坎吗?      不敢说什么大话,但是我有一个心得,学习算法,一定要理解,理解比会写更重要,会写,很有可能仅仅是记忆好, 但是过一段时间忘了, 就对这个算法完全没有印象了,我就是这样。   所以我以后学习算法,一定抱着理解的心态,理解了,就很好。 第二章:基本排序算法 2.1 冒泡排序   人们常说,冒泡排序是最初级的排序算法,人们说这句话的时候是从时间复杂度这个角度来说的,这么说或许没错, 但是,冒泡排序是相当漂亮的排序,这个“漂亮”是说,假如把排序算法可视化起来,x轴从小到大,依次对应0到n,y轴对应的是a[x], 然后排序开始了,你会发现冒泡很飘逸,看起来很赏心悦目,大概人们都喜欢美丽的泡泡吧。    冒泡排序的中心思想: 不写中心思想至少也有十年了吧,记得高中之后语文老师就不搞什么中心思想之类的。 但是我还是要写一写冒泡排序的中心思想,而且,现在我不看资料,我想描述一下,看一看我到底能不能描述。   冒泡排序的思想是这样的,从数组a[0]开始,比较相邻的两项的大小顺序,假如顺序不对,则交换两项。 5 4 6 3 2   比如上面的数组