最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

C語言排序算法的幾種實(shí)現(xiàn)過程

 更新時間:2026年04月16日 10:53:36   作者:0302huang  
本文介紹了四種排序算法的思想:冒泡排序通過相鄰比較交換實(shí)現(xiàn),選擇排序通過每次選出最小值實(shí)現(xiàn),插入排序通過將當(dāng)前元素插入到有序序列實(shí)現(xiàn),快速排序通過挖坑填數(shù)遞歸實(shí)現(xiàn),每種算法都有其適用場景和優(yōu)缺點(diǎn)

一、冒泡排序

思想:

相鄰的兩個數(shù)比較,若不符合關(guān)鍵字排序順序,則交換,外層循環(huán)n-1輪,內(nèi)層循環(huán)如果從0開始向右比較,則外層循環(huán)每輪得到一個最大的數(shù),(內(nèi)層循環(huán)若從下標(biāo)n-1開始向左比較,則外層循環(huán)每輪得到一個最小的數(shù))循環(huán)n-1輪則排序完成。

void bubblesort(int *a,int n){
	int i,j;
	for(i=0;i<n-1;i++){//N-1輪循環(huán) 
		for(j=0;j<n-1-i;j++){//j<n-1-i 小優(yōu)化 
			if(a[j]>a[j+1]){
				swap(&a[j],&a[j+1]);
			}
		}
	}
}
//雙向冒泡排序
void bidbubblesort(int *a,int n){
	int i,j;
	int left,right;
	left=0;right=n-1;
	while(left<right){
		for(i=left;i<right;i++){
			if(a[i]>a[i+1]){
				swap(&a[i],&a[i+1]);
			}
		} //從左向右比較,會出現(xiàn)一個最大的數(shù)在最右邊 
		right--;
		for(i=right;i>left;i--){
			if(a[i]<a[i-1]){
				swap(&a[i],&a[i-1]);
			}
		} //從右向左比較,會出現(xiàn)一個最小的數(shù)在最左邊 
		left++;
	}
}

二、選擇排序

思想:

每次進(jìn)入外層循環(huán),都要先設(shè)置最小值(或最大值)下標(biāo)min_pos為當(dāng)前i的值,讓內(nèi)層循環(huán)的循環(huán)變量從i的下一個開始遍歷,與a[min_pos]進(jìn)行比較,如果a[i]<a[min_pos],則要讓min_pos=i;內(nèi)層循環(huán)就是為了找到一個最小值的下標(biāo)賦值給min_pos,出了內(nèi)循環(huán),則交換a[i]和a[min_pos]。

i ++;循環(huán)下去最終循環(huán)n-1次,得到n-1個最小值,則排序完畢

void selectsort(int *a,int n){
	int i,j,min_pos;
	//每一次從新進(jìn)入循環(huán)都要先設(shè)置最小值的下標(biāo)min_pos是當(dāng)前i的值 
	for(i=0;i<n-1;i++){
		min_pos=i;
		for(j=i+1;j<n;j++){//從min_pos的下一個開始遍歷數(shù)組,與a[min_pos]比較,記錄最小值的下標(biāo) 
			if(a[j]<a[min_pos]) {
				min_pos=j;
			}
		}
		if(min_pos!=i){
			swap(&a[i],&a[min_pos]);
		}
	}
}
//逆向選擇排序
void selectsort(int *a,int n){
	int i,j,max_pos;
	for(i=n-1;i>0;i--){ //每一次從新進(jìn)入循環(huán)都要先設(shè)置最大值的下標(biāo)max_pos是當(dāng)前i的值
		max_pos=i; //設(shè)置假設(shè)最大值下標(biāo)  
		for(j=i-1;j>=0;j--){ //j從最大值下標(biāo)的前一個開始,與最大值比較直到j(luò)=0 
			if(a[j]>a[max_pos]){
				max_pos=j;
			}
		}
		if(max_pos!=i){
			swap(&a[max_pos],&a[i]);
		}
	}
}
//雙向選擇排序
void bidselectsort(int *a,int n){
	int i,j;
	int left,right;
	int min_pos,max_pos;
	left=0;
	right=n-1;
	while(left<right){
		max_pos=right;
		min_pos=left;
		for(i=left+1;i<=right;i++){
			if(a[i]<a[min_pos]){
				min_pos=i;
			}
		}
		if(min_pos!=left){
			swap(&a[min_pos],&a[left]);
		}
		left++;
		for(i=right-1;i>=left;i--){
			if(a[i]>a[max_pos]){
				max_pos=i;
			}
		}
		if(max_pos!=right){
			swap(&a[max_pos],&a[right]);	
		}
        right--;	
	}
}

三、插入排序

思路:

核心是從0--0天然有序,到0--1有序,......再到0--n-1有序,因此外層循環(huán)從i=1開始代表先做0--1有序,當(dāng)i循環(huán)到n-1時,則0--n-1有序了,排序完畢,外層到內(nèi)層的連接處,需要設(shè)置當(dāng)前的a[i]=temp,方便后續(xù)的操作(比較大小和插入)。

內(nèi)層循環(huán),遵循“往前看”的原則,j=i-1開始一直到j(luò)>=0,其實(shí)意思是比較temp與前面元素的相對大小,如果前面某個元素比temp小,則可以break,因?yàn)榍懊娑际怯行虻?,一定也會比temp更小。

若前面的某個元素比temp大,則應(yīng)將它后移一位故a[j+1]=a[j];

void insertsort(int *a,int n){
	int temp;
	int i,j;
	for(i=1;i<n;i++){//從0-1有序到0-n-1有序 
		temp=a[i];
		for(j=i-1;j>=0;j--){//往前看 
			if(a[j]<temp) break;		
			else{
				a[j+1]=a[j];//將現(xiàn)在這個下標(biāo)j的數(shù)后移一位,那應(yīng)該就是移到下標(biāo)為j+1的位置 
			}
		}//出循環(huán)的條件是break或者j=-1; 此時應(yīng)該將a[j+1]=temp; 
		a[j+1]=temp;
	}
}

四、快速排序

思想:

挖坑填數(shù)+遞歸 定義一個基準(zhǔn)數(shù)std=a[0],定義左右下標(biāo)left right,定義一個決策變量(決定哪個下標(biāo)移動)moving。

若moving==2,則應(yīng)該移動右下標(biāo)right,從std的右邊  希望去找到一個比std要小的數(shù),放到左下標(biāo)的位置上,(因?yàn)榘補(bǔ)[0]取出來當(dāng)做std,a[0]一開始是一個坑);如果沒找到就right--,繼續(xù)找;若找到了,需要三步操作,填數(shù) 改決策變量 移動下標(biāo)。

循環(huán)下去當(dāng)left==right時,則把a(bǔ)[left]=std;最后核心是遞歸,需要注意參數(shù),傳入數(shù)組的首地址和數(shù)組std左邊和右邊的元素個數(shù)。

void quicksort(int *a,int n)
{
	if(n<2){//數(shù)組的元素少于兩個就不用排序了 
		return;
	}
	//遞歸調(diào)用時,std、left,right都是相應(yīng)的參數(shù),這樣寫是沒問題的
	int std=a[0];	//選取數(shù)組第一個數(shù)作為中心軸 (基準(zhǔn)數(shù)) 
	int left=0;		//左下標(biāo)  
	int right=n-1;	//右下標(biāo) 
	int moving=2;	//判斷當(dāng)前應(yīng)當(dāng)移動哪個下標(biāo),1-左下標(biāo),2-右下標(biāo) 
	while(left<right)
	{
		if(moving==2)//移動右下標(biāo)的情況 
	//此時應(yīng)當(dāng)找出一個數(shù) 比基準(zhǔn)數(shù)std 小的數(shù) 放到左邊多出來的坑位 
		{
			if(std<a[right])
	//如果右下標(biāo)位置元素的值大于等于基準(zhǔn)數(shù),則右下標(biāo)繼續(xù)向左移動 
			{
				right--; 
			}
			else
			//如果右下標(biāo)位置元素的值小于基準(zhǔn)數(shù),那么把右下標(biāo)的元素填到左下標(biāo)的坑中 
			{ 	//三步操作:填數(shù),改決策變量,移動下標(biāo) 
				a[left]=a[right];
				left++;		//讓左下標(biāo)向右移動
				moving=1;	//改變 決定移動哪個下標(biāo)的變量moving,使得下次循環(huán)將移動左下標(biāo) 
				continue;
			}	
		} 
		if(moving==1)//移動左下標(biāo)的情況 
//此時應(yīng)當(dāng)找出一個比基準(zhǔn)數(shù)std要大的數(shù) 放到此時右下標(biāo)多出來的坑位 
		{
			if(a[left]<std)//如果左下標(biāo)位置元素的值小于std基準(zhǔn)數(shù),則左下標(biāo)繼續(xù)向右移動 
			{
				left++;
			} 
			else//如果左下標(biāo)位置元素的值大于std基準(zhǔn)數(shù),將該值填到右下標(biāo)的坑位 
			{
				a[right]=a[left];
				right--;	//讓右下標(biāo)向左移動 
				moving=2;	//改變 決定移動哪個下標(biāo)的變量moving,使得下次循環(huán)將移動右下標(biāo) 
			} 
		} 
	}
	//此時一輪循環(huán)結(jié)束,left應(yīng)該等于right,將此時的坑位填入std基準(zhǔn)數(shù) 
	a[left]=std;//此時基準(zhǔn)數(shù)的位置是在left這里 
	//這樣基準(zhǔn)數(shù)的左邊是有 0-left-1,即left個元素 
	//這樣基準(zhǔn)數(shù)的右邊是有 n-left-1 個元素 (右邊就等于全部減去左邊再減去中間一個元素) 
	//遞歸調(diào)用該函數(shù),只是傳進(jìn)去的參數(shù)需要調(diào)整使得,每次調(diào)用函數(shù)的范圍合理 
	quicksort(a,left);//對上一次基準(zhǔn)數(shù)的左邊進(jìn)行排序   
	quicksort(a+left+1,n-left-1);//對上一次的基準(zhǔn)數(shù)的右邊進(jìn)行排序 
	//注意傳入的參數(shù)是 數(shù)組和數(shù)組元素個數(shù),這個仔細(xì)分析一下就行,傳入數(shù)組的首地址
}	

總結(jié)

以上為個人經(jīng)驗(yàn),希望能給大家一個參考,也希望大家多多支持腳本之家。

相關(guān)文章

  • C語言編程中建立和解除內(nèi)存映射的方法

    C語言編程中建立和解除內(nèi)存映射的方法

    這篇文章主要介紹了C語言編程中建立和解除內(nèi)存映射的方法,分別為mmap()函數(shù)和munmap()函數(shù)的使用,需要的朋友可以參考下
    2015-08-08
  • 一文詳解C++ 智能指針的原理、分類及使用

    一文詳解C++ 智能指針的原理、分類及使用

    智能指針的本質(zhì)就是使用一個對象來接管一段開辟的空間,這篇文章就來給大家介紹介紹C++智能指針的原理,分類及使用方法,文中有詳細(xì)的代碼示例,需要的朋友可以參考下
    2023-05-05
  • C語言之包含min函數(shù)的棧實(shí)例詳解

    C語言之包含min函數(shù)的棧實(shí)例詳解

    這篇文章主要為大家詳細(xì)介紹了C語言之包含min函數(shù)的棧,文中示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下,希望能夠給你帶來幫助
    2022-02-02
  • Qt使用TabWidget實(shí)現(xiàn)多窗體功能

    Qt使用TabWidget實(shí)現(xiàn)多窗體功能

    Qt 是一個跨平臺C++圖形界面開發(fā)庫,利用Qt可以快速開發(fā)跨平臺窗體應(yīng)用程序,在Qt中我們可以通過拖拽的方式將不同組件放到指定的位置,本章將重點(diǎn)介紹TabWidget標(biāo)簽組件的常用方法及靈活運(yùn)用,需要的朋友可以參考下
    2023-12-12
  • C++聯(lián)合體union用法實(shí)例詳解

    C++聯(lián)合體union用法實(shí)例詳解

    這篇文章主要介紹了C++聯(lián)合體union用法,較為詳細(xì)的分析了C++中聯(lián)合體的概念、實(shí)用技巧及相關(guān)注意事項(xiàng),需要的朋友可以參考下
    2015-05-05
  • C++11/14如何使用typedef和using定義類型別名和別名模版

    C++11/14如何使用typedef和using定義類型別名和別名模版

    這篇文章主要介紹了C++11/14如何使用typedef和using定義類型別名和別名模版
    2023-04-04
  • C++模擬Linux Shell編寫一個自定義命令

    C++模擬Linux Shell編寫一個自定義命令

    這篇文章主要介紹了C++如何模擬Linux Shell實(shí)現(xiàn)編寫一個自定義命令,本文通過實(shí)例代碼進(jìn)行命令行解析,代碼簡單易懂,對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2022-12-12
  • C++中的內(nèi)存對齊實(shí)例詳解

    C++中的內(nèi)存對齊實(shí)例詳解

    這篇文章主要介紹了C++中的內(nèi)存對齊實(shí)例詳解的相關(guān)資料,這里不僅提供實(shí)現(xiàn)方法及代碼還提供了手工制作圖,來幫助到大家理解這部分知識,需要的朋友可以參考下
    2017-07-07
  • C++兩個cpp文件間如何進(jìn)行各自函數(shù)的調(diào)用方式

    C++兩個cpp文件間如何進(jìn)行各自函數(shù)的調(diào)用方式

    這篇文章主要介紹了C++兩個cpp文件間如何進(jìn)行各自函數(shù)的調(diào)用方式,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2023-02-02
  • Windows下Qt打包自動尋找依賴的DLL

    Windows下Qt打包自動尋找依賴的DLL

    本文介紹了兩種在Windows下使用Qt打包應(yīng)用程序并自動尋找依賴DLL的方法,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2024-12-12

最新評論

安塞县| 衡阳县| 金溪县| 镇坪县| 怀安县| 晋州市| 弋阳县| 郧西县| 江源县| 苗栗市| 固原市| 开远市| 邛崃市| 安陆市| 蚌埠市| 朝阳市| 改则县| 华安县| 玛沁县| 青岛市| 阳原县| 正镶白旗| 阳谷县| 瑞金市| 开远市| 张北县| 来凤县| 大丰市| 南郑县| 抚顺市| 台北县| 锡林郭勒盟| 察隅县| 济阳县| 金溪县| 南京市| 基隆市| 醴陵市| 大石桥市| 安徽省| 娱乐|