冒泡算法
思路: 在要排序的一组数中,对当前还未排好序的范围内的全部数,自上而下对相邻的两个数依次进行比较和调整,让较大的数往下沉,较小的往上冒。
即:每当两相邻的数比较后发现它们的排序与排序要求相反时,就将它们互换
/*最简单的冒泡算法
* N个数,比较(N-1)次,而随着比较的次数的增加,每次要进行比较的数据依次减少。
* 每趟比较下来都会确定一个数的位置
*/
public class BubbleSort {
public static void main(String[] args) {
int arr[] = {33,12,39,88,36,77,55,1,2,34,120,119};
for(int i = 0; i < arr.length -1 ; i++){ //控制排序趟数
for(int j = 0; j < arr.length - 1 - i; j++){ //控制每次比较的数的个数
//小值交换到前面
if(arr[j] > arr[j+1]){
int temp = arr[j];
arr[j] = arr[j+1];
arr[j+1] = temp;
}
}
System.out.println("第"+(i+1)+"次排序的结果");
for(int a=0;a<arr.length; a++){
System.out.print(arr[a] + "\t");
}
System.out.println("");
}
System.out.println("最终的排序结果:");
for(int a = 0;a < arr.length; a++){
System.out.print(arr[a]+"\t");
}
}
}
选择排序
思路:从0索引开始,依次和后面元素比较,小的往前放,第一次完毕,最小值出现在了最小索引处,第二次找到第二小的值。
/*选择排序
*每一次比较都会确定一个最小的值
*/
public class SelectSort {
public static void main(String[] args) {
int arr[] = {33,12,39,88,36,77,55,1,2,34,120,119};
for(int i = 0; i < arr.length; i++){ //控制比较的次数
int min = i; //记录最小值的位置
for(int j = i+1; j < arr.length; j++){ //控制每次比较的数个数
if(arr[min] > arr[j]){
min = j;
}
}
int temp = arr[i];
arr[i] = arr[min];
arr[min] = temp;
System.out.println("第"+(i+1)+"次排序的结果");
for(int a=0;a<arr.length; a++){
System.out.print(arr[a] + "\t");
}
System.out.println("");
}
System.out.println("最终的排序结果:");
for(int a = 0;a < arr.length; a++){
System.out.print(arr[a]+"\t");
}
}
}
快速排序
思路:对于给定的一组记录,选择一个基准元素,通常选择第一个元素或者最后一个元素,通过一趟扫描,将待排序列分成两部分,一部分比基准元素小,一部分大于等于基准元素,此时基准元素在其排好序后的正确位置,然后再用同样的方法递归地排序划分的两部分,直到序列中的所有记录均有序为止。(实现平衡二叉树)
//快速排序
public class QuickSort{
public static void main(String[] args) {
int arr[] = {33,12,39,88,36,77,55,1,2,34,120,119};
sort(arr , 0 , arr.length-1);
System.out.println("排序后的结果:");
for(int x : arr){
System.out.print(x+" ");
}
}
//将数组的某一段元素进行划分,小的在左,大的在右
public static int divide(int[] a,int start,int end){
//每次都以最右边的元素作为基准值
int base = a[end];
//start一旦等于end,就说明左右两个指针合并到了同一位置,可以结束此轮循环
while(start < end ){
while(start < end && a[start] <= base)
//从左边开始遍历,如果比基准值小,就继续往右走
start++;
//上面的while循环结束时,就说明当前的a[start]的值比基准值大,应与基准值进行交换
if(start < end){
//交换
int temp = a[start];
a[start] = a[end];
a[end] = temp;
//交换后,此时的那个被调换的值也同时调到了正确的位置(基准值右边),因此右边也要同时向前移动一位
end--;
}
while(start < end && a[end] >= base)
//从右边开始遍历,如果比基准值大,就继续向左走
end--;
//上面的while循环结束时,就说明当前的a[end]的值比基准值小,应与基准值进行交换
if(start < end){
//交换
int temp = a[start];
a[start] = a[end];
a[end] = temp;
//交换后,此时的那个被调换的值也同时调到了正确的位置(基准值左边),因此左边也要同时向后移动一位
start++;
}
}
//这里返回start或者end皆可,此时的start和end都为基准值所在的位置
return end;
}
//排序
public static void sort(int[] a, int start, int end){
if(start > end){
//如果只有一个元素,就不用再排下去
return;
}else {
//如果不止一个元素,继续划分两边递归排序下去
int partition = divide(a, start, end);
sort(a, start, partition-1);
sort(a, partition+1, end);
}
}
}