日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

      
          
      歡迎訪問 生活随笔!

      生活随笔

      當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

      编程问答

      排序算法的代码--选择排序综合训练题

      發布時間:2023/12/18 编程问答 22 豆豆
      生活随笔 收集整理的這篇文章主要介紹了 排序算法的代码--选择排序综合训练题 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

      目錄

      冒泡和快速的改進???

      綜合應用題


      冒泡和快速的改進???

      綜合應用題

      1、題目:編寫雙向冒泡算法,在正反兩個方向交替進行掃描,即第一趟把關鍵字最大的元素放在序列的最后面,第二趟把關鍵字最小的元素放在序列的最前面,如此反復進行。

      解析:

      這種排序叫做雙向起泡。奇數趟時,從前往后比較相鄰元素的關鍵字,遇到逆序即交換,直到把序列中關鍵字最大的元素移動到序列尾部。偶數趟時,從后往前比較相鄰元素的關鍵字,遇到逆序即交換,直到把序列中關鍵字最小的元素移動到序列尾部。

      #include <stdio.h> #include <stdbool.h>typedef int ElemType; ElemType a[50];//a[]待排序序列void swap(int *a, int *b) {int temp;temp = *a;*a = *b;*b = temp; }void BubbleSort(ElemType a[], int n) {int low = 0, high = n-1,i;bool flag = true;while (low < high && flag){flag = false;//每一趟開始之前都需要將標志歸0.//奇數趟,正向走,將最大的移動到最后。for ( i = low; i < high; i++){if (a[i] > a[i+1]){swap(&a[i],&a[i+1]);flag = true;//發生交換} }high --;//偶數趟,倒向走,將最小的移動到最前面。for ( i = high; i > low; i--){if (a[i] < a[i-1]){swap(&a[i],&a[i-1]);flag = true;}}low ++;} }int main() {int n;printf("請輸入序列個數:\n");scanf("%d",&n);printf("請輸入序列中的元素: \n");for (int i = 0; i < n; i++){scanf("%d",&a[i]);}BubbleSort(a,n);printf("排序好的序列是:\n");for (int i = 0; i < n; i++){ printf("%d,",a[i]);}printf("\n");return 0; }

      結果:

      請輸入序列個數:
      10
      請輸入序列中的元素:?
      12 13 39 43 10 33 23 90 82 19
      排序好的序列是:
      10,12,13,19,23,33,39,43,82,90

      自己敲的過程中出現的不足之處:

      1、沒有想過雙向冒泡以后,每趟排序的起始點和結尾點都會變,要添加low和high。還在那啥傻傻的想。。。廢物。。。

      2、你是憨熊嗎?為什么不考慮一下是否要判斷越界等情況,只知道寫排序過程,就沒有想過結束條件是什么嗎?

      我希望你可以記住!!!判斷結束條件!!!

      3、那么怎么才是排序結束呢?當然是用flag來標志每一次是否排序,若排序則對flag進行改變。

      在定義bool flag = true時,我一開始初始定義成了flag = flase,然后,

      因為只有true時while才執行,那么我只能把對flag的判斷放在了while循環里面。

      因為每趟排序后,flag=true,所以在while循環的開頭增加判斷:若flag = false則說明沒有進行交換對叭?然后跳出循環。

      造成了一個后果:是不是傻,是不是傻,一開始你自己規定的就是flag = false呀!!!。所以一遍也不執行,直接跳出。。。

      我說怎么排序后沒有發生變化。。。害… …

      2、已知線性表按順序存儲,且每個元素都是不相同的整形元素,設計把所有奇數移動到所有偶數前邊的算法(要求時間最少,輔助空間最少)。

      解析:我的看法:沒什么新穎的。重點是要求時間最少,輔助空間最少,。那也就是說,循環嵌套層數要少,盡量在原序列上進行移動。????????????????????????????????????????????????????????????????????????????????????????????????王道:本題可基于快速排序的劃分思想來設計算法:只需要遍歷一次即可。時間復雜度為O(n),空間復雜度O(1),基本思想:先從前向后找到一個偶數元素L(i),再從后向前找到一個奇數元素L(i),將二者交換;重復上述過程,直到low>high。(不完全使用快速排序)。

      #include <stdio.h>typedef int ElemType; ElemType a[50];void swap(int *a, int *b) {int temp;temp = *a;*a = *b;*b = temp; }void move(ElemType a[],int n) {int low = 0, high = n-1;while (low < high){while (low < high && a[low] % 2 != 0){//只要是奇數就跳過,直到找到一個偶數,跳出while循環。low ++;}while (low < high && a[high] % 2 != 1){//只要是偶數就跳過,直到找到一個奇數,跳出while循環。high --;}if (low < high){swap(&a[low], &a[high]);//交換。}low ++; high --;//我居然把這一條件給忘了,不加這一句,i和j的值就一直不變,就會死循環。} }int main() {int n;printf("請輸入序列個數:\n");scanf("%d",&n);printf("請輸入序列中的元素: \n");for (int i = 0; i < n; i++){scanf("%d",&a[i]);}move(a,n);printf("排序好的序列是:\n");for (int i = 0; i < n; i++){ printf("%d,",a[i]);}printf("\n");return 0; }

      總結一下:1、main函數里好像都差不多,那以后就不寫了。2、在考試里遇到要求時間最少、算法最優等等,或者沒有暗示又不是超級適合其他排序算法的,那就從快速排序開始試試。

      3、試重新編寫考點精析中的快速排序的劃分算法,使之每次選取的樞軸值都是隨機地從當前子表中選擇的。

      pass吧? 使用隨機數來選出pivot.但是,選出的隨機數要和第一個元素進行交換,pivot還是=a[low]。

      4、試編寫一個算法,使之能夠在數組L[1…n]中找出第k小的元素(即從小到大排序后處于第k個位置的元素)。

      解析:

      我的想法是直接對數組進行排序,然后提取L(k),便得到了第k小。但是,這樣其平均時間復雜度將達到O(nlog2n)以上。

      王道:可以采用小根堆的思想,時間復雜度為O(n+klog2n).

      最精彩的還是基于快速排序的劃分操作。

      主要思想:

      5、荷蘭國旗問題:設有一個僅有紅、白、藍三種顏色的條塊組成的條塊序列,請編寫一個時間復雜度為 Q ( n ) Q(n) Q(n)的算法,使得這些條塊按紅、白、藍的順序排好,即排成荷蘭國旗圖案。
      6、【2016年統考真題】已知由n(n≥2)個正整數構成的集合 A = {ak ∣ 0 ≤ k < n} ,將其劃分為兩個不相交的子集A1和 A2,元素個數分別是n1和n2,A1和A2中的元素之和分別為S1和S2。設計一個盡可能高效的劃分算法,滿足 |n1 ? n2|最小且 |S1 ? S2|最大。
      要求:

      1、給出算法的基本設計思想。

      2、根據設計思想,采用C語言描述算法,關鍵之處給出注釋。

      3、說明你所設計算法的平均時間復雜度和空間復雜度。

      總結

      以上是生活随笔為你收集整理的排序算法的代码--选择排序综合训练题的全部內容,希望文章能夠幫你解決所遇到的問題。

      如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。