java实现排序

冒泡排序

每次排序都会把最大的元素放到最后一个位置,排序的时候和冒泡很像,一个一个的冒泡。

java 复制代码
//冒泡排序,每次把一个排好的数字放在最后的位置
    public static void bubbleSort(int []nums){
        int n= nums.length;
        int end=n-1;
        while(true){
            int exchange=0;//记录每层循环中数据交换的次数
            for(int i=0;i<end;i++){
                if(nums[i]>nums[i+1]){
                    swap(nums,i,i+1);
                    exchange++;
                }
            }
            if(exchange==0)break;//交换次数为零说明交换完毕
        }

    }

快速排序,使用的是分段排序的方法,每次以第一个元素作为标准值,然后从后往前遍历,找到第一个比标准值小的元素,和low位置交换。接着就从前往后遍历,找到第一个比标准值大的元素,交换位置。

java 复制代码
 //快速排序
    public static void quickSort(int[]nums,int i,int j){
        if(i<j){
            int part=partition(nums,i,j);
            quickSort(nums,i,part-1);
            quickSort(nums,part+1,j);
        }
    }
    public static int partition(int[]nums,int low,int high){
        int tmp=nums[low];//第一个元素作为标准
        while(low<high){
            //从后往前找到第一个小于tmp的元素
            while(low<high&&nums[high]>=tmp){
                high--;
            }
            if(low<high){
                nums[low]=nums[high];
            }
            //从前往后找到第一个大于tmp的元素
            while(low<high&&nums[low]<=tmp){
                low++;
            }
            if(low<high){
                nums[high]=nums[low];
            }
        }
        nums[low]=tmp;
        return low;
    }

插入排序,从第二个元素开始,然后往前遍历,如果这个元素比当前索引位置的元素大,这个元素就需要后移动。

java 复制代码
//插入排序,每次枚举当前位置的元素,然后往前遍历,比自己大的元素往后移动
    public static void insertSort(int []nums){
        int n=nums.length;
        for(int i=1;i<n;i++){
            int tmp=nums[i];
            int j=i-1;
            //往前搜索,遇到比当前元素大的往后移动
            while(j>=0&&nums[j]>=tmp){
                nums[j+1]=nums[j--];
            }
            nums[j+1]=tmp;
        }
    }

希尔排序,步长不是1,而是d。

java 复制代码
//希尔排序
    public static void shellSort(int[]nums){
        int len=nums.length;
        for(int d=len/2;d>0;d/=2){
            for(int i=d;i<len;i++){
                int tmp=nums[i];
                int j;
                for(j=i-d;j>=0;j-=d){
                    if(nums[j]>=tmp){
                        nums[j+d]=nums[j];
                    }else{
                        break;//退出循环
                    }
                }
                nums[j+d]=tmp;
            }
        }
    }

选择排序,每次选择最小的元素,进行交换位置

java 复制代码
 //选择排序,每次找到最小的元素,与当前位置直接交换
    public static void selectSort(int[]nums){
        int n=nums.length;
        for(int i=0;i<n-1;i++){
            int k=i;//记录当前的位置
            for(int j=i+1;j<n;j++){
                //循环找到一个最小的
                if(nums[j]<=nums[k])k=j;
            }
            if(k!=i){
                swap(nums,i,k);
            }
        }
    }

堆排序

java 复制代码
public static void heapSort(int[]nums){
        int n=nums.length-1;
        //进行筛选,n/2是第一个非叶子节点
        for(int i=n/2;i>=0;i--){
            heapShift(nums,i,n);
        }
        //大根堆构建完毕,开始排序,每次从堆顶获取最大的元素放在数组的最后一个位置
        for(int i=n;i>0;i--){
            int tmp=nums[0];
            nums[0]=nums[i];
            nums[i]=tmp;
            heapShift(nums,0,i-1);
        }

    }
    public static void heapShift(int []nums,int i,int n){
        //从i到n是满足大根堆的
        int tmp=nums[i];
        int j=i*2+1;//左子树节点,完全二叉树
        while(j<=n){
            if(j<n&&nums[j]<nums[j+1]){
                j++;//变成右子树
            }
            if(tmp>nums[j])break;//筛选结束
            nums[i]=nums[j];//大的元素往上移动
            i=j;
            j=2*j;
        }
        nums[i]=tmp;
    }

归并排序,先分治到数组的个数只有一个的时候,再使用两个数组进行合并

java 复制代码
public static int[] mergeSort(int[]nums){
        return divide(nums,0,nums.length);
    }
    public static int[]divide(int[]nums,int i,int j){
        int m=j-i;
        if(j-i==0){
            return new int[]{};
        }
        if(j-i==1){
            return new int[]{nums[i]};
        }
        int[]left=divide(nums,i,i+m/2);
        int[]right=divide(nums,i+m/2,j);
        return merge(left,right);
    }
    public static int[]merge(int[]left,int[]right){
        int[]p=new int[left.length+right.length];
        int k=0;
        int i=0;
        int j=0;
        while(i<=left.length-1&&j<=right.length-1){
            if(left[i]<right[j]){
                p[k++]=left[i++];
            }else{
                p[k++]=right[j++];
            }
        }
        while(i<=left.length-1){
            p[k++]=left[i++];
        }
        while(j<=right.length-1){
            p[k++]=right[j++];
        }
        return p;
    }

桶排序(计数排序),使用一个数组记录每个元素出现的次数。

maxLength>Math.max(nums)

java 复制代码
//桶排序,就是使用一个数组,下标的位置就是某个元素
    public static void bulkSort(int[]nums,int maxLength){
        int[]max=new int[maxLength];
        for(int num:nums){
            max[num]++;
        }
        for(int i=0,j=0;i<maxLength;i++){
            while(max[i]!=0){
                nums[j++]=i;
                max[i]--;
            }
        }
    }
相关推荐
czhc11400756631 小时前
c# 1121 构造方法
java·javascript·c#
Z***25802 小时前
Java爬虫框架
java·开发语言·爬虫
晓华-warm2 小时前
Warm-Flow 1.8.4 票签新增多种通过率策略!
java·中间件·流程图·jar·开源软件·工作流
m***11902 小时前
【SpringBoot】Spring Boot 项目的打包配置
java·spring boot·后端
fei_sun2 小时前
【数据结构】2018年真题
数据结构
limenga1022 小时前
支持向量机(SVM)深度解析:理解最大间隔原理
算法·机器学习·支持向量机
李慕婉学姐2 小时前
Springboot剪纸数字博物馆系统6wd19a3a(程序+源码+数据库+调试部署+开发环境)带论文文档1万字以上,文末可获取,系统界面在最后面。
java·spring boot·后端
coder江2 小时前
二分查找刷题总结
算法
SundayBear2 小时前
C语言复杂类型声明完全解析:从右左原则到工程实践
c语言·开发语言·数据结构·嵌入式