1. 程式人生 > >用回撥函式實現氣泡排序

用回撥函式實現氣泡排序

(一)什麼是回撥函式呢?

答:回撥函式就是通過函式指標呼叫的函式。如果你把函式的指標(地址)作為引數傳遞給另一個函式,當這個指標被用為呼叫它所指向的函式時,我們就說這是回撥函式。

(二)回撥函式的實現機制

1.定義一個回撥函式

2.提供函式實現的一方在初始化時。將回調函式的函式指標註冊給呼叫者。

3.當特定的條件發生時,呼叫者使用函式指標呼叫回撥函式對事件進行處理。

(三)回撥函式的使用原因

通過回撥函式,可以將呼叫者與被呼叫者分開。

可能你不知道,在庫函式中有一個qsort函式,即我們通常說的快速排序,讓我們看它是如何呼叫和實現的。

原型:void qsort( void *base, size_t

num, size_twidth

           int (__cdecl *compare) (const void *elem1, const void *elem2) )

base:目標陣列的首位置

num:元素個數

width:每個元素所佔位元組數

compare:函式指標,指向一個比較函式

#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#include<stdlib.h>
#include<string.h>


int compare_int(const void *elem1,const void *elem2)//排序整型陣列
{
    return *(int *)elem1-*(int *)elem2;
}

int compare_float(const void *elem1,const void *elem2)//排序浮點型陣列
{
	if((*(float *)elem1)-(*(float *)elem2) > 0)//不可以直接返回二者的差,\
		                                     轉化為整型時可能漏掉部分資料     
         return 1;

	else if((*(float *)elem1)-(*(float *)elem2) == 0)
         return 0;

	else
         return -1;
}

int compare_string(const void *elem1,const void *elem2)、
{
    return strcmp(*(char **)elem1,*(char **)elem2);//應先找到每個字串\
	                                                 的首地址再進行解引用
}

void print_int_arr(int arr[],int sz)
{
    int i = 0;
	for(i=0; i<sz; i++)
	{
	    printf("%d ",arr[i]);
	}
	printf("\n");
}
void print_float_arr(float arr[],int sz)
{
    int i = 0;
	for(i=0; i<sz; i++)
	{
	    printf("%f ",arr[i]);
	}
	printf("\n");
}
void print_string_arr(char **arr,int sz)
{
    int i = 0;
	for(i=0; i<sz; i++)
	{
	    printf("%s ",arr[i]);
	}
	printf("\n");
}
int main()
{
	int arr1[]={2,4,6,8,0,1,3,5,7,9};
	int sz1 = sizeof(arr1)/sizeof(arr1[0]);
	float arr2[]={2.0f,4.4f,6.5f,8.3f,0.0f,1.2f,3.7f,5.6f,7.9f,9.8f};
	int sz2 = sizeof(arr2)/sizeof(arr2[0]);
	char *arr3[]={"abcd", "bbdd", "aabc", "dfer","dghjf"};
	int sz3 = sizeof(arr3)/sizeof(arr3[0]);
	qsort(arr1,sz1,sizeof(int),compare_int);
	qsort(arr2,sz2,sizeof(int),compare_float);
	qsort(arr3,sz3,sizeof(int),&compare_string);
	print_int_arr(arr1,sz1);
	print_float_arr(arr2,sz2);
	print_string_arr(arr3,sz3);
	system("pause");
	return 0;
}

程式執行結果:


是的,你沒看錯,通過回撥函式,我們同時排序了不同型別的陣列元素,是不是很方便呢,同時讓程式也更靈活了。

通過上面的呼叫和部分實現,讓我們來一起模擬一個通過回撥函式實現氣泡排序的演算法吧!

#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#include<stdlib.h>
#include<string.h>

int compare_int(const void *elem1,const void *elem2)
{
    return *(int *)elem1-*(int *)elem2;
}

int compare_float(const void *elem1,const void *elem2)
{
	if((*(float *)elem1)-(*(float *)elem2) > 0)//不可以直接返回二者的差,\
		                                       //轉化為整型時可能漏掉部分資料     
         return 1;   

	else if((*(float *)elem1)-(*(float *)elem2) == 0)
         return 0;

	else
         return -1;
}

int compare_double(const void *elem1,const void *elem2)
{
	if((*(double *)elem1)-(*(double *)elem2) > 0)//不可以直接返回二者的差,\
		                                     //轉化為整型時可能漏掉部分資料     
         return 1;

	else if((*(double *)elem1)-(*(double *)elem2) == 0)
         return 0;

	else
         return -1;
}

int compare_char(const void *elem1,const void *elem2)
{
    return *(char *)elem1-*(char *)elem2;//應先找到每個字串\
	                                     // 的首地址再進行解引用
}

int compare_string(const void *elem1,const void *elem2)
{
    return strcmp(*(char **)elem1,*(char **)elem2);//應先找到每個字串\
	                                               // 的首地址再進行解引用
}

void Swap(size_t width,void *n1,void *n2)
{
    char tmp = 0;
	size_t i = 0;
	for(i=0; i<width; i++)
	{
	    tmp=*((char *)n1+i);
		*((char *)n1+i)=*((char *)n2+i);
		*((char *)n2+i)=tmp;
	}
}
void bubble_sort(void *base,size_t sz,size_t width,
	            int (*compare)(const void*,const void*))
{
    size_t i = 0;
	size_t j = 0;
	for(i=0; i<sz-1; i++)
	{
	    for(j=0; j<sz-1-i; j++)
		{
		    <span style="color:#ff0000;">if(compare(((char*)base+j*width),((char *)base+(j+1)*width))>0)//升序
			//if(compare((char *)base+j*width),(char *)base+(j+1)*width)>0)//降序
			Swap(width,((char *)base+j*width),((char *)base+(j+1)*width));</span>
		}
	}
}
void print_int_arr(int arr[],int sz)
{
    int i = 0;
	for(i=0; i<sz; i++)
	{
	    printf("%d ",arr[i]);
	}
	printf("\n");
}
void print_float_arr(float arr[],int sz)
{
    int i = 0;
	for(i=0; i<sz; i++)
	{
	    printf("%f ",arr[i]);
	}
	printf("\n");
}
void print_double_arr(double arr[],int sz)
{
    int i = 0;
	for(i=0; i<sz; i++)
	{
	    printf("%lf ",arr[i]);
	}
	printf("\n");
}
void print_char_arr(char arr[],int sz)
{
    int i = 0;
	for(i=0; i<sz; i++)
	{
	    printf("%c ",arr[i]);
	}
	printf("\n");
}
void print_string_arr(char *arr[],int sz)
{
    int i = 0;
	for(i=0; i<sz; i++)
	{
	    printf("%s ",arr[i]);
	}
	printf("\n");
}
int main()
{
	int arr1[]={2,4,6,8,0,1,3,5,7,9};
	int sz1 = sizeof(arr1)/sizeof(arr1[0]);
	float arr2[]={2.0f,4.4f,6.5f,8.3f,0.0f,1.2f,3.7f,5.6f,7.9f,9.8f};
	int sz2 = sizeof(arr2)/sizeof(arr2[0]);
	double arr3[]={1.1,2.4,3.5,4.6,7.8,9.0};
	int sz3 = sizeof(arr3)/sizeof(arr3[0]);
	char arr4[]={'d','f','b','c','e','g','h','a'};
	int sz4 = sizeof(arr4)/sizeof(arr4[0]);
	char *arr5[]={"abcd", "bbdd", "aabc", "dfer","dghjf"};
	int sz5 = sizeof(arr5)/sizeof(arr5[0]);
	bubble_sort(arr1,sz1,sizeof(int),compare_int);
	bubble_sort(arr2,sz2,sizeof(float),compare_float);
	bubble_sort(arr3,sz3,sizeof(double),compare_double);
	bubble_sort(arr4,sz4,sizeof(char),compare_char);
	bubble_sort(arr5,sz5,sizeof(char *),compare_string);
	print_int_arr(arr1,sz1);
	print_float_arr(arr2,sz2);
	print_double_arr(arr3,sz3);
	print_char_arr(arr4,sz4);
	print_string_arr(arr5,sz5);
    system("pause");
	return 0;
}


各種型別的資料都可呼叫一個函式來排序了,怎麼樣,你學會了嗎?

相關推薦

函式實現氣泡排序

(一)什麼是回撥函式呢? 答:回撥函式就是通過函式指標呼叫的函式。如果你把函式的指標(地址)作為引數傳遞給另一個函式,當這個指標被用為呼叫它所指向的函式時,我們就說這是回撥函式。 (二)回撥函式的實現機制 1.定義一個回撥函式 2.提供函式實現的一方在初始化時。將回調函式的

【C語言】 使用函式實現氣泡排序

實現功能:既能排序整型數,也可以排序字串 程式碼如下: #include <stdio.h> #include <string.h> int int_cmp(const v

【C/C++】函式實現計算器

一、問題概述 用C語言實現一個簡易計算器,可以用來實現加減乘除的功能 名詞解釋: 函式指標:一個指標,用於指向一個函式 函式指標陣列:是一個數組,裡面存放多個函式指標 回撥函式:一個函式,若引數中有函式指標,那麼這個函式便是回撥函式 二、問題分析 這個問題大可用switc

簡單函式指標陣列和函式實現計算器

利用函式指標陣列簡單實現計算器 函式指標陣列:以char *(*p[3])(char *)為例解釋,這是一個數組,陣列名為p,陣列記憶體儲了3個指向函式的指標 這些指標指向一些返回值型別為指向字元的指

26、【支付模組開發】——支付寶函式實現和查詢使用者訂單狀態介面編寫

####1、支付寶回撥函式實現 我們在除錯支付寶沙箱環境的時候,支護寶會有一個回撥函式,也就是在支付成功之後,可以呼叫我們支付之後需要執行的相關方法,從而達到資料庫的資料和我們的操作相統一。 首先我們先在本地將回調函式編寫好~ 在OrderController類中新建我們的支付寶回撥函式

關於ssm,前臺html頁面jquery的success函式實現跳轉重新整理問題

$(function(){ $.ajax({ type:“post”, url:"…/…/b/k.action", dataType: “json”, success:function(data){ $(data).each(function(k,v){ $("tbody").a

Java JNA (二)—— dll函式實現

java呼叫dll檔案需要使用回撥函式作為公開函式的引數時,用以下方法實現: 首先,看c++中定義的dll公開函式: typedef void (*ccback)(char *name ,int length); int dllFunction(char *ip, i

js中的函式封裝,函式實現的簡單動畫效果

                   js實現的簡單動畫效果 一、js實現的簡單動畫       1、此程式碼中運用了js中的建構函式,函式封裝,回撥函式,函式內的正負值的判            

JS 和 ajax 實現網路請求 和 對應的類封裝 函式實現

先上效果圖 如下: 1、使用ajax 實現網路請求 程式碼如下: function HttpRequest(){ // document.alert('進入這個方法'); //使用 api 框架 跨域 請求

C++函式模板實現氣泡排序

         此程式為從小到大排序,這個程式比較精彩的部分就是加入了false,大致思路為:當一個數字比它後面的數字小時,不執行if(a[j]>a[j+1])語句。減少了執行次數。(直接把含有flag的語句注掉,編譯也可以通過)。寫程式時應該注意的是第6 、14 、

谷歌的AsyncHttpClient簡單模仿安卓的AsyncHttpClient,實現非同步請求函式返回值

實現思路 既然要呼叫Future.get() 才能激發訪問,那麼就想到了使用一個執行緒去訪問。我們就不需要等待阻塞了。 模仿安卓的AsyncHttpClient回撥。根據狀態回撥不同的函式。 實現的效果 執行程式碼...

11月6日排序函式,匿名函式函式,遞迴函式, zip函式

##### 排序sort, sorted的區別: list.sort(func=None, key=None, reverse=False(or True)) 對於reverse這個bool型別引數,當reverse=False時:為正向排序;當reverse=True時:為方向排序。預設為Fal

C語言函式熟練—使用方法(構建程式框架方便好

通俗點不行嗎?啊,不行嗎?老外把國人玩的都不是人了。國人還自己玩自己。非把一個簡單的東西複雜化。叫那麼難理解!!窩裡鬥。。。。。。典型!!!!!!!! 不說那麼複雜的,誰是狗屎,豬屎。就說怎麼用回撥。使用步驟: 1.寫一個函式A,A裡面有一個引數是個指標函式 比如: int shao(in

Java——Java實現氣泡排序,選擇排序,快速排序和二分查詢

在學習C語言時,就有講過這三個排序演算法和二分查詢的演算法。 以下是用Java來實現氣泡排序(Bubble Sort)演算法,選擇排序(Selection Sort),快速排序(Quick Sort)和二分查詢(Binary Search) package pra_07;

C語言實現氣泡排序

  #include <stdio.h> #define MAX 11 int main(int argc, const char *argv[]) { int a[MAX] = {0}; int i, j, t; char ch; /*輸入資

java實現氣泡排序和選擇排序

氣泡排序:依次比較兩個相鄰的元素,將值大的元素交換至右端,一輪比較過後,最大的元素在最右端。 public class BubbleSort { public static void main(String[] args) { int[] arr

Qt 學習之路 2(19):事件的接受與忽略(當重寫事件回撥函式時,時刻注意是否需要通過呼叫父類的同名函式來確保原有實現仍能進行!有好幾個例子。為什麼要這麼做?而不是自己去手動呼叫這兩個函式呢?因為我們無法確認父類中的這個處理函式有沒有額外的操作)

版本: 2012-09-29 2013-04-23 更新有關accept()和ignore()函式的相關內容。 2013-12-02 增加有關accept()和ignore()函式的示例。 上一章我們介紹了有關事件的相關內容。我們曾經提到,事件可以依情況接受和忽略。現在,我們就

JS實現函式

場景:             現在我要建立一個地圖,建立成功之後,執行回撥函式,整個過程有點類似於前端向後臺傳送請求,成功之後拿到結果執行回撥函式。 程式碼: <script> function createMap (){ var opti

C語言實現氣泡排序—2

隨機輸入N個數據(亂序),進行排序輸出 #include <stdio.h> int main(int argc, const char *argv[]) { int a[100] = {0}; int i, j, t; int n = 0; char

Uncaught ReferenceError: jp2 is not defined,jsonp抓取qq音樂總是說函式沒有定義

問題如下參考連結:https://segmentfault.com/q/1010000010051040 用jsonp抓取qq音樂總是說回撥函式沒有定義, 我的要實現時候的步驟 1。第一步 我要實現的目的 問題:如題 我的部分程式碼: import originJSON