算法复习-3种较高级排序

1.归并排序:它先将要排序的数组递归地分成两半分别排序,然后再将结果归并起来。要做到这一点首先需要一种原地归并两半数组的方法,该方法的思想为先将所有数组复制到一个辅助数组aux[]中,然后再归并到a[]中,也就说将数组按下标i=lo~mid,j=mid+1~hi两部分进行大小比较然后依次返回原数组之中,在比较的时候需要添加一下判定条件
1.左半边用完,i>mid,则直接把右半边剩余数组依次放入原数组之中,j++
2.右半边用完,j>hi,则直接把左半边剩余数组依次放入原数组之中,i++
3.如果右边元素小于左边元素,则将右边元素放回原数组之中,j++
4.如果左边元素小于右边元素,则将左边元素放回原数组之中,i++

public void mergesort(int[] a)
{
   public  aux=new int[a.length];
   sort(a,0,a.length-1);
}
public void sort(int[] a,int lo,int hi)
{

if(hi<=lo)
return;
int mid=lo+(hi-lo)/2;
sort(a,lo,mid);
sort(a,mid+1,hi);
merge(a,lo,mid,hi);

}

public void merge(int a[],int lo,int mid,int hi)
{
   int i=lo;
   int j=mid+1;
   for(int k=lo;k<=hi;k++)
     aux[k]=a[k];
   for(int k=lo;k<=hi;k++)
   {
       if(i>mid) a[k]=aux[j++];
       else if(j>hi) a[k]=aux[i++];
       else if(less(aux[j],aux[i]))  a[k]=a[j++];//less函数之前的初级排序里面有
       else a[k]=a[i++];
}
}

2.快速排序:快速排序是一种分治的排序算法,它将通过一个切分值分成两个部分,一部分的值都不大于这个切分值,另一部分的值都大于这个切分值,分别对这个两个部分进行排序,当两个子数组由序的时候,整个数组就有序了。

public void  quickSort(int[] a)
{
sort(a,0,a.length-1);
}
public void sort(int[] a,int lo,int hi)
{
  if(lo>=hi)return;
  int j=partition(a,lo,hi);
  sort(a,lo,j);
  sort(a,j+1,hi);
}
public int partition(int[] a,int lo,int hi)
{
    int i=lo;
    int j=hi;
    int mid=(lo+hi)/2;
    int v=a[mid];
    while(true)
    {
      while(less(a[i++],v)) if(i>=hi)break;
      while(less(v,a[j--]))if(j<=lo)break;
      if(i>=j)break;//从左扫描找到大于切分值的数,之后从右向做扫描找到小于切分值的数
      exch(a,i,j);
}
exch(a,mid,j);//将切分值放入正确的位置
return j;
}

3.堆排序:要使用堆排序,首先使用一个数组来表示一个完全二叉树的节点。将数组进行堆的下沉操作,使得整个堆有序,为一个最大值堆,顶点为最大的一个值。然后将顶点与数组最后一个值进行交换,然后对顶点进行下沉操作,让顶点为剩余数组中最大的,直到堆中还剩一个顶点时,排序完成

public void heapsort(int a)
{
    int N=a.length;
    for(int k=N/2;k>=1;k--)
     sink(a,k,N);
    while(N>1)
     {
         exch(a,1,N--);
         sink(a,1,N);
}
public void sink(int[] a,int k,int N)
{
   while(2*k<=N)
   {
      int j=2*k;
      if(j<N&&less(a[j],a[j+1]))j++;
      if(!less(a[k,a[j]]))break;
      exch(a,k,j);
      k=j;//这个操作是寻找当前节点的子节点比它大的值中的最大值进行交换
}
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值