Langage C - pointeurs avancés (2)

Table des matières

7. Tableau de pointeurs de fonction

8. Pointeur vers un tableau de pointeurs de fonction

9. Fonction de rappel

fin


7. Tableau de pointeurs de fonction

Pour parler franchement, un tableau de pointeurs de fonction signifie ajouter [ ] après le nom du pointeur de fonction, et les deux sont combinés pour former un tableau.

Alors, à quoi sert ce tableau de pointeurs de fonctions ? Ne vous inquiétez pas, utilisons un code de fonction de calculatrice pour vous donner quelques idées.

Il s'agit d'un code de calculatrice simple qui calcule des nombres en sélectionnant différentes fonctions pour saisir différentes fonctions.

void menu()
{
	printf("***********************\n");
	printf("*****1.add   2.sub*****\n");
	printf("*****3.mul   4.div*****\n");
	printf("*****0.exit       *****\n");
	printf("***********************\n");
}
int Add(int x, int y)
{
	return x + y;
}
int Sub(int x, int y)
{
	return x - y;
}
int Mull(int x, int y)
{
	return x * y;
}
int Div(int x, int y)
{
	return x / y;
}

int main()
{
	int input = 0;
	int x = 0;
	int y = 0;
	int ret = 0;
	do
	{
		menu();
		printf("请选择:");
		scanf("%d", &input);
		
		switch (input)
		{
		case 1:
			printf("请输入两个数字:\n");
			scanf("%d %d", &x, &y);
			ret = Add(x, y);
			printf("%d\n", ret);
			break;
		case 2:
			printf("请输入两个数字:\n");
			scanf("%d %d", &x, &y);
			ret = Sub(x, y);
			printf("%d\n", ret);
			break;
		case 3:
			printf("请输入两个数字:\n");
			scanf("%d %d", &x, &y);
			ret = Mull(x, y);
			printf("%d\n", ret);
			break;

		case 4:
			printf("请输入两个数字:\n");
			scanf("%d %d", &x, &y);
			ret = Div(x, y);
			printf("%d\n", ret);
			break;

		case 0:
			printf("退出程序\n");
			break;

		default :
			printf("输入错误,请重新输入:\n");




		}

		
	} while (input);


	return 0;
	
}

Mais de cette façon, nous trouverons un problème : lorsque nous essayons d'ajouter plus de fonctions, le commutateur deviendra plus long et plus compliqué.

En analysant le code, nous pouvons savoir que les fonctions de chaque fonction sont en réalité différentes, mais les paramètres formels qu'elles utilisent et les types de fonctions qu'elles représentent sont les mêmes. 

Modifions ensuite le code :

Supprimez d’abord la partie commutateur et remplacez-la par un tableau de pointeurs de fonction.

Vous pouvez voir que les indices ici ne correspondent pas à la sélection de notre calculatrice.A ce moment, NULL peut être utilisé pour occuper une position dans le tableau.

Ensuite, utilisez simplement l’instruction conditionnelle if pour implémenter la fonction.

8. Pointeur vers un tableau de pointeurs de fonction

Si vous êtes intéressé, vous pouvez l'utiliser comme extension pour en savoir plus~

Un pointeur pointant vers un tableau de pointeurs de fonction est essentiellement un pointeur, donc l'objet de stockage doit être l'adresse du tableau de pointeurs de fonction.

Le pointeur dont nous avons besoin est entouré de (*p)pour garantir qu'il s'agit d'un pointeur et non d'un tableau. Ici, pfArr est simplifié en p pour une identification facile. Finalement, cela devient un pointeur vers ce tableau. Le but est de pointer vers un tableau, pas de devenir un tableau.

9. Fonction de rappel

Revenons à la partie code du switch pour implémenter la fonction de rappel : on peut d'abord encapsuler une fonction, puis appeler la partie similaire du code 4 fois.

C'est la magie de la fonction de rappel. Utilisez un pointeur de fonction pour accepter la fonction requise. Dans la fonction calc, utilisez le pointeur qui a accepté l'adresse de la fonction pour saisir les paramètres réels.

Compréhension approfondie des fonctions de rappel :

Comme c’est l’ancienne règle, utilisons des exemples simples pour aider tout le monde à comprendre, puis nous en apprendrons davantage sur les merveilleuses utilisations de qsort. Commençons par un exemple classique : le tri à bulles.

En fait, le tri des bulles est très simple : pour 10 éléments, l'élément doit être échangé au pire 9 fois, et pour n éléments, il doit être échangé n-1 fois. Chaque fois que l'élément suivant est parcouru, le contraste sera réduit de un.

En fait, cette fonction n’est pas assez générale, elle ne permet de trier que des entiers.

Nous présenterons ensuite la fonction qsort, cette fonction de tri universelle.

Grâce à cela nous savons que les méthodes de comparaison de deux données du même type sont différentes.

On peut alors en déduire que le quatrième paramètre formel de qsort est de fournir une méthode de comparaison entre deux données. Nous pouvons imaginer transférer respectivement 9 et 8 dans le tri à bulles d'appel vers e1 et e2, et les laisser comparer en cmp. Cependant, vous rencontrerez un problème à ce moment-là : *e1 fera une erreur car le type void* ne peut pas être déréférencé.

Le véritable rôle de void* est d'accepter des pointeurs de différents types :

Par conséquent, si vous souhaitez implémenter une comparaison de tailles entières, vous ne pouvez d'abord forcer la conversion.

La règle de cmp est que lorsque l'élément pointé par p1 > l'élément pointé par p2, un nombre supérieur à 0 est renvoyé, s'il est égal, 0 est renvoyé, et s'il est inférieur à 0, un nombre inférieur à 0 est renvoyé.

Exécutez le code et le tri est réussi. En fait, la partie la plus critique de qsort est le quatrième paramètre formel. Vous devez créer une méthode de comparaison correspondant au type de données avant de pouvoir l'exécuter. Par exemple, les entiers peuvent être comparés en utilisant <>, les structures peuvent être comparées en utilisant des longueurs de chaîne. , etc.

 

Testons le tri des structures :

Vient maintenant la partie la plus critique de la création d’une fonction de comparaison.

 

 Essayez à nouveau de comparer par nom. Pour le moment, le nom est une chaîne et le signe moins ne peut pas être utilisé pour exprimer le résultat. Vous pouvez utiliser la fonction strcmp pour comparer des chaînes. Par coïncidence, le type de retour de strcmpd est cohérent avec le retour règle de cmp.

 

Le tri entre les chaînes est comparé dans l'ordre du dictionnaire. Par exemple, abc et aq. Les deux a sont identiques au début, mais le q suivant est plus grand que b, donc abc est classé devant aq.

fin

La partie la plus intéressante de cet article est le tri qsort. Il est différent de notre type de tri traditionnel. Il est plus diversifié et nous donne plus d'idées de tri.

Je suppose que tu aimes

Origine blog.csdn.net/fax_player/article/details/132779429
conseillé
Classement