嗨,我有以下的設計,我不知道,如果在一般的C編譯器(GCC或鐺)將嘗試解決在編譯時的函數指針或將它永遠離開它,直到運行時間。編譯時間函數PTR提領
在test.h:
typedef struct array_ {
size_t size;
void *array;
size_t (*get_size)(struct array_ *);
} array_t;
static inline size_t
get_size (array_t *A) {
return A->get_size(A);
}
在test.c的:
#include <stdio.h>
#include <stdlib.h>
#include "test.h"
static size_t _get_size (array_t *A) {
return A->size;
}
int main(void)
{
array_t *A = malloc(sizeof(array_t));
A->size = 3;
A->array = (int[]){1,2,3};
A->get_size = _get_size;
printf("%llu\n", A->get_size(A));
printf("%llu\n", get_size(A));
return 0;
}
我的問題是 - 將A-> get_size(A)在編譯時被解析到_get_size(A)或甚至可能是A->大小?是A-> get_size()總是比get_size(A)更高效,或者它們編譯成幾乎相同的東西?
我知道我要問什麼編譯器會或不會做的是依賴於編譯器和其他的東西(如優化級),但總體上有一個答案還是隻是取決於太多的事情?
編輯:我省略了錯誤檢查的清晰度。
編輯:「gcc -S」代碼。我認爲一個指針正被取消引用。
main:
.LFB4:
.cfi_startproc
pushq %rbp
.cfi_def_cfa_offset 16
.cfi_offset 6, -16
movq %rsp, %rbp
.cfi_def_cfa_register 6
subq $32, %rsp
movl $24, %edi
call malloc
movq %rax, -24(%rbp)
movq -24(%rbp), %rax
movq $3, (%rax)
movl $1, -16(%rbp)
movl $2, -12(%rbp)
movl $3, -8(%rbp)
movq -24(%rbp), %rax
leaq -16(%rbp), %rdx
movq %rdx, 8(%rax)
movq -24(%rbp), %rax
movq $_get_size, 16(%rax)
movq -24(%rbp), %rax
movq 16(%rax), %rax
movq -24(%rbp), %rdx
movq %rdx, %rdi
call *%rax
movq %rax, %rsi
movl $.LC0, %edi
movl $0, %eax
call printf
movq -24(%rbp), %rax
movq %rax, %rdi
call get_size
movq %rax, %rsi
movl $.LC0, %edi
movl $0, %eax
call printf
movl $0, %eax
leave
.cfi_def_cfa 7, 8
ret
.cfi_endproc
正如您正確觀察,「它取決於」。您可以嘗試使用具有各種優化選項的'-S'編譯器選項(編譯爲彙編),並查看生成的彙編代碼以查看編譯器在每種情況下所做的工作。 (編輯:這是海灣合作委員會,我不知道什麼標誌給叮噹)。 – 2014-12-06 19:12:14
我做到了。 「clang -S」與「gcc -S」相同。以上是gcc反彙編(不優化)。鐺產生非常不同的拆卸,與「-O3」更加不同。 – s5s 2014-12-06 19:25:26