Quand utiliser la fonction comme les macros en C
Je lisais un peu de code écrit en C ce soir, et au sommet de
le fichier a été la fonction-comme macro HASH:
#define HASH(fp) (((unsigned long)fp)%NHASH)
Cette gauche me demandais, pourquoi devrait-on choisir de mettre en œuvre un
fonction de cette manière d'utiliser une fonction comme macro au lieu de la mise en œuvre de
comme un régulier à la vanille fonction C? Quels sont les avantages et les
les inconvénients de la mise en œuvre?
Merci beaucoup!
Comme les fonctions de hachage aller, c'est assez faible - mais alors, il semble que les données qu'il a à traiter est assez simple aussi.
En fait, il n'est pas très vif pour en faire un
En fait, il n'est pas très vif pour en faire un
macro
. Un inline fonction statique c'est probablement plus approprié. C a eu inline depuis 1999 et gcc
avant même que. Cette question a été cité comme faisant double emploi avec kfifo utilisation de définit. Si le MS-Windows est la raison pour laquelle les gens disent cette macro est raisonnable, comment sont-ils liés?OriginalL'auteur Ralph | 2009-10-24
Vous devez vous connecter pour publier un commentaire.
Macros comme permettant d'éviter la surcharge d'un appel de fonction.
Il pourrait ne pas sembler beaucoup. Mais dans votre exemple, la macro se transforme en 1-2 instructions en langage machine, en fonction de votre CPU:
alors que la fonction d'un équivalent serait beaucoup plus d'instructions en langage machine, généralement quelque chose comme
Beaucoup plus de code, hein? Si vous êtes en train de faire quelque chose comme le rendu de chacun des dizaines de milliers de pixels dans une fenêtre dans une interface graphique, les choses se passent beaucoup plus vite si vous utilisez la macro.
Personnellement, je préfère utiliser C++ en ligne, comme étant plus lisible et moins sujettes à l'erreur, mais inlines sont aussi beaucoup plus d'une indication pour le compilateur qui il n'a pas à prendre. Les macros du préprocesseur sont d'un marteau le compilateur ne peut pas discuter avec.
C'est ce que les fonctions inline sont pour! 🙂
LiraNuna: inline fonctions ne font pas partie de la norme ANSI C90, qui est ce que la plupart des compilateurs de soutien. Ils sont seulement en C99, ou C++
C99 est, bien sûr, de dix ans maintenant. N'importe quel compilateur C qui ne supporte pas c'est à faire sérieusement de la date.
dites-le à Microsoft!
OriginalL'auteur Bob Murphy
Un avantage important de la macro-fonction de mise en œuvre, c'est qu'il n'est pas lié à un béton de type de paramètre. Une fonction-comme macro dans C agit, à bien des égards, comme un modèle de fonction en C++ (templates en C++ sont nés comme "plus civilisé" macros, BTW). Dans ce cas particulier, l'argument de la macro n'a pas de type de béton. Il peut être absolument tout ce qui est convertible de type
unsigned long
. Par exemple, si l'utilisateur afin de lui plaît (et s'ils sont prêts à accepter la mise en œuvre définies par les conséquences), ils peuvent passer les types pointeur à cette macro.De toute façon, je dois admettre que cette macro n'est pas le meilleur exemple de type indépendant de la flexibilité des macros, mais, en général, de flexibilité, ce qui est pratique assez souvent. Encore une fois, lorsque certaines fonctionnalité est implémentée par une fonction, il est limité à certains types de paramètres. Dans de nombreux cas, afin d'appliquer la même opération pour les différents types, il est nécessaire de prévoir plusieurs fonctions avec différents types de paramètres (et des noms différents, puisque c'est C), tandis que la même chose peut être fait par une seule fonction-comme macro. Par exemple, la macro
fonctionne avec tous les arithmétiques types, tandis que la fonction de base de la mise en œuvre doit fournir un certain nombre d'eux (je suis ce qui implique la norme
abs
,labs
,llabs
etfabs
). (Et oui, je suis conscient de ce qui est traditionnellement mentionné les dangers d'une telle macro).Les Macros ne sont pas parfaits, mais la maxime populaire à propos de "fonction-comme les macros ne sont plus nécessaires en raison de fonctions inline" est tout simplement absurde. Afin de remplacer entièrement la fonction-comme les macros C va avoir besoin de modèles de fonction (comme en C++) ou au moins de surcharge de fonctions (comme en C++). Sans que la fonction comme les macros sont et resteront très utile intégrer l'outil dans C.
OriginalL'auteur AnT
D'une part, les macros sont mauvais parce qu'ils sont fait par le préprocesseur, qui ne comprend rien à propos de la langue et du texte-remplacer. Ils ont généralement beaucoup de limitations. Je ne peux pas voir l'un au-dessus, mais, habituellement, les macros sont moches solutions.
D'autre part, ils sont parfois même plus rapide qu'un
static inline
méthode. J'ai été fortement de l'optimisation d'un programme court et a constaté que l'appel à unstatic inline
méthode prend deux fois plus de temps (juste les frais généraux, pas à proprement parler un corps de la fonction) par rapport à une macro.Outil? Vim,
gprof
, et le vénérabletime
de commande.gprof
est un très bon générateur de profils avec une faible surcharge, mais vous devez être prudent, car il ne suit pas les macros (il ne les voit pas; un autre de macros ses inconvénients).La version de compilateur utilisais-tu, et quel est le niveau d'optimisation ont été en vous demandant de lui?
gcc version 4.3.3 (Ubuntu 4.3.3-5ubuntu4)
(g++). L'optimisation a été-O3
.OriginalL'auteur
Le plus courant (et le plus souvent à tort) des raisons que les gens donnent pour l'utilisation de macros (en "plain old C") est l'efficacité d'un tel argument. À l'aide de leur efficacité est très bien si vous avez réellement profilé votre code et sont l'optimisation d'un véritable goulot d'étranglement (ou l'écriture d'une fonction de bibliothèque qui peut être un goulot d'étranglement pour quelqu'un un jour). Mais la plupart des gens qui insistent sur l'utilisation d'entre eux n'ont Pas réellement analysé rien et sont juste de créer de la confusion où il n'apporte pas de bénéfice.
Les Macros peuvent également être utilisées pour une pratique de recherche et remplacement type de substitutions laquelle le langage C n'est pas capable de faire.
Certains problèmes que j'ai eu dans le maintien de code écrit par les macro-agresseurs, c'est que les macros peuvent paraître assez comme pour les fonctions, mais n'apparaissent pas dans la table de symboles, de sorte qu'il peut être très ennuyeux pour retrouver la trace de leur retour à leurs origines dans tentaculaire codesets (où est cette chose?!). L'écriture de macros dans TOUS les BOUCHONS est évidemment utile pour les futurs lecteurs.
Si elles sont plus assez simples substitutions, ils peuvent aussi créer de la confusion si vous avez à l'étape à la trace à travers eux avec un débogueur.
Code-la création de lignes de ce type: #define COLORVAL(couleur,val) int couleur##_nombre = val; je ne vais pas le faire moi-même trop, mais si vous avez besoin de lignes pour le rouge, le bleu, le vert, ..., noir, alors il peut vous aider.
p.212 de la "Unix Hater s Handbook" (p.248 dans le .pdf simson.net/ref/ugh.pdf, de cs.washington.edu/homes/weise/uhh-download.html) décrit certaines difficultés liées à l'.
OriginalL'auteur Kilo
Votre exemple n'est pas vraiment une fonction à tous,
Je pensais, c'était juste une façon d'écrire un code plus lisible avec le casting et mod opration enveloppé dans une seule macro"
HASH(fp)
'Maintenant, si vous décidez d'écrire une fonction pour cela, il serait probablement ressembler,
Tout à fait inutile pour une fonction comme ça,
OriginalL'auteur nik
La Préprocesseur C peut être utilisé pour créer des fonctions inline. Dans votre exemple, le code s'affiche à l'appel de la fonction de HACHAGE, mais au contraire c'est juste le code en ligne.
Les avantages de faire des macro-fonctions ont été éliminés lors de la C++ introduit les fonctions inline. De nombreux anciens de l'API comme MFC et ATL toujours utiliser les fonctions de macro pour faire de préprocesseur trucs, mais il ne laisse que le code compliqué et plus difficile à lire.
OriginalL'auteur Andrew Keith