C Language
inlining
Ricerca…
Funzioni di allineamento utilizzate in più di un file sorgente
Per le piccole funzioni che vengono richiamate spesso, l'overhead associato alla chiamata di funzione può essere una frazione significativa del tempo di esecuzione totale di tale funzione. Un modo per migliorare le prestazioni, quindi, è eliminare il sovraccarico.
In questo esempio utilizziamo quattro funzioni (più main()
) in tre file sorgente. Due di questi ( plusfive()
e timestwo()
) vengono richiamati dagli altri due situati in "source1.c" e "source2.c". Il main()
è incluso quindi abbiamo un esempio funzionante.
main.c:
#include <stdio.h>
#include <stdlib.h>
#include "headerfile.h"
int main(void) {
int start = 3;
int intermediate = complicated1(start);
printf("First result is %d\n", intermediate);
intermediate = complicated2(start);
printf("Second result is %d\n", intermediate);
return 0;
}
source1.c:
#include <stdio.h>
#include <stdlib.h>
#include "headerfile.h"
int complicated1(int input) {
int tmp = timestwo(input);
tmp = plusfive(tmp);
return tmp;
}
source2.c:
#include <stdio.h>
#include <stdlib.h>
#include "headerfile.h"
int complicated2(int input) {
int tmp = plusfive(input);
tmp = timestwo(tmp);
return tmp;
}
headerfile.h:
#ifndef HEADERFILE_H
#define HEADERFILE_H
int complicated1(int input);
int complicated2(int input);
inline int timestwo(int input) {
return input * 2;
}
inline int plusfive(int input) {
return input + 5;
}
#endif
Le funzioni timestwo
e plusfive
vengono richiamate sia da complicated1
sia da complicated2
, che si trovano in "unità di traduzione" o file sorgente diversi. Per utilizzarli in questo modo, dobbiamo definirli nell'intestazione.
Compilare in questo modo, assumendo gcc:
cc -O2 -std=c99 -c -o main.o main.c
cc -O2 -std=c99 -c -o source1.o source1.c
cc -O2 -std=c99 -c -o source2.o source2.c
cc main.o source1.o source2.o -o main
Utilizziamo l'opzione di ottimizzazione -O2 perché alcuni compilatori non sono in linea senza l'ottimizzazione attivata.
L'effetto della parola chiave inline
è che il simbolo della funzione in questione non viene emesso nel file oggetto. Altrimenti si verificherà un errore nell'ultima riga, dove stiamo collegando i file oggetto per formare l'eseguibile finale. Se non avessimo in inline
, lo stesso simbolo verrebbe definito in entrambi i file .o
e si verificherebbe un errore "simbolo definito in più punti".
In situazioni in cui il simbolo è effettivamente necessario, questo ha lo svantaggio che il simbolo non viene prodotto affatto. Ci sono due possibilità per affrontarlo. Il primo è aggiungere una dichiarazione extern
extra delle funzioni inline esattamente in uno dei file .c
. Quindi aggiungi quanto segue a source1.c
:
extern int timestwo(int input);
extern int plusfive(int input);
L'altra possibilità è definire la funzione con static inline
anziché inline
. Questo metodo ha l'inconveniente che alla fine una copia della funzione in questione può essere prodotta in ogni file oggetto prodotto con questa intestazione.