3大类6种排序 插入排序 选择排序 冒泡排序 希尔排序 堆排序 快速排序 —————— 开开开山怪

<1>选择排序

void chooseSort(int *array, int count) {
//第一轮找到数组中最小的放在数组第一个位置
//第二轮除过第一个元素之外,在剩下的元素中找到第二小的放在数组的第二个位置
//第三轮除过前两个元素之外,在剩下的元素中找到第三小的放在数组的第三个位置
//以此类推

 int index;
 int i = 0;
 int j = 0;
 int temp; 
 
 for (i = 0; i < count - 1; i++)  {
   for(index = i, j = i; j < count; j++) {//设每一轮的第一个元素为当前最小元素,则最小元素的小标为i
     if (array[index] > array[j]) {//自己先和自己进行比较,再和之后的元素进行比较
       index = j;    
     }   
    }
                      //如果index == i 则表示这一轮中最小的元素就是本轮第一个
                    //如果本身数组中的数据按照升序排列,那么每一轮的最小元素的下标就是本轮的第一个元素的下标
                    //此时的if语句里边的操作将不会在进行,时间复杂度可以减少3n
                    
  if (index != i) { //此判断表示找到的最小元素的下标不是每轮一开始设定的最小值的下标,
   temp = array[index];
   array[index] = array[i];
   array[i] = temp;
   
  }
 }
 
}

<2> 插入排序


void insertSort(int *array, int count) {
 int index;
 int i = 0;
 int temp;
 int j;
 
 for (index = 1; index < count; index++) {
  //将index对应的值与index之前的下标进行相比较进行插入定位
  //再进行移动
  temp = array[index];
  for(i = 0; i < index && temp > array[i]; i++) {
  //进行比较定位 
  //当条件为temp > array[i]的时候,如果有两个相同的数字,排列完之后总是之前的顺序逆序出现
  //当条件为temp >= array[i]的时候,如果有两个相同的数字,排列完之后按之前的顺序出现
  }
  
  for (j = index; j > i; j--) {
   array[j] = array[j - 1];
  }
  
  array[i] = temp;
  
 }
 
}

<3>冒泡排序


void swapSort(int *array, int count) {
 int i = 0;
 int j = 0;
 int temp;
 boolean exchange = FALSE;
 
 for (i = 0; i < count; count--) {
  for (j = 0, exchange = FALSE; j < count - 1; j++) {
   if (array[j] > array[j + 1]) {
    temp = array[j + 1];
    array[j + 1] = array[j];
    array[j] = temp; 
    exchange = TRUE;   
   }
  }
  if (exchange == FALSE) {
   break;   
  }
  
 }
 
}

<4>希尔排序


void stepInsertSort(int *array, int count, int i, int step) {
 int index;
 int temp;
 int j = 0;
 int k = 0;
 
 for (index = i + step; index < count; index += step) {
  temp = array[index];
  
  for (j = i; j < index && temp > array[j]; j += step) {
   
  }
  for (k = index; k > j; k -= step) {
   array[k] = array[k - step];
  }
  array[j] = temp;
  
 }
}


void shellSort(int *array, int count) {
 int step;
 int i = 0;
 
 for (step = count / 2; step > 0; step /= 2) {//每一次的step的变化都要做一次整体的每一组交换
  for (i = 0; i < step; i++) {
   stepInsertSort(array, count, i, step);
   //插入排序,只不过不是挨个向后取元素进行定位移动,而是选取每隔step个的元素进行处理   
  }  
 }
}

<5>堆排序


void heapOnce(int *array, int count, int root) {
 int leftIndex;
 int rightIndex;
 int maxIndex;
 int temp;
 
 while(root < count / 2) {//保证了只有非叶子节点才有左右孩子
  
  temp = array[root];
  leftIndex = 2 * root + 1;
  rightIndex = 2 * root + 2;
  
  if (rightIndex >= count) {//表明没有右孩子,
   maxIndex = leftIndex;
  } else {//左右孩子中选出最大值对应的下标,另一边的根堆保持不变
   if (array[rightIndex] > array[leftIndex]) {
    maxIndex = rightIndex;
   } else {
    maxIndex = leftIndex;
   }
  }
  if (temp < array[maxIndex]) {//根据大小比较交换位置
   array[root] = array[maxIndex];
   array[maxIndex] = temp;
   root = maxIndex;
  } else {
   return;
  }
    
 }
 
 
}

void heapSort(int *array, int count) {
 int temp;
 int i;
 
 for (i = count / 2 - 1; i > 0; i--) {//先整体做一次大根堆处理,以后只需要处理根节点就行
  heapOnce(array, count, i);
 }
 
 while (count > 1) {
  heapOnce(array, count, 0);//最后一层的大根堆处理,以后每次只需要进行根节点的调整
  
//交换根节点和最后一个节点的位置
  temp = array[0];
  array[0] = array[count - 1];
  array[count - 1] = temp;
 
  count--;  
  
 }
 
}

<6> 快速排序


int quickOnce(int *array, int head, int tail) {
 int temp = array[head];
 
 while (head < tail) {
  while (head < tail && array[tail] > temp) {
   --tail;
  }
  if(head < tail) {//采用if做判断,避免是原本是升序的情况下,tail一直--,只到head与tail相等
                  //此时并不需要做交换,只有在head < tail的情况下才需要作交换
   array[head++] = array[tail];
   
  }
  while (head < tail && array[head] < temp) {
   ++head;
  }
  if (head < tail) {
   array[tail--] = array[head];
   
  }
 }
 array[head] = temp;
 
 return head;
 
}

void  quickDG(int *array, int head, int tail) {
 int middle;
 if (head >= tail) {
  return;
 }
 middle = quickOnce(array, head, tail);
 quickDG(array, head, middle - 1);
 quickDG(array, middle + 1, tail); 
}

void quickSort(int *array, int count) {
 
 quickDG(array, 0, count - 1);
 
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值