前言:
這篇文章記錄的是我在學習Linux C編程一站式學習是關於函數返回指標這節時遇到的問題,由於是新手,下面的小程式讓我費解了半天,最終用gdb調試情況下分析明白了代碼的原理。
本文:
下面是關於函數返回指標的一個小樣本:
/* ret_ptr.h */#ifndef RET_PTR_H#define RET_PTR_Hextern char *get_a_day(int idx);#endif
/* ret_ptr.c */#include <string.h>#include "ret_ptr.h"static const char *msg[] = {"Sunday", "Monday", "Tuesday", "Wednesday","Thursday", "Friday", "Saturday"};char *get_a_day(int idx){ static char buf[20]; strcpy(buf, msg[idx]); return buf;}
/* main.c */#include <stdio.h>#include "ret_ptr.h"int main(void){ printf("%s %s/n", get_a_day(0), get_a_day(1)); return 0;}
本以為程式的運行結果是Sunday Monday,但卻相差甚遠。
運行結果為:Sunday Sunday
用GDB進行分析
get_a_day (idx=1),而不是按照get_a_day (0),get_a_day (1)的順序執行,這時buf的內容為Monday
當兩次調用get_a_day後才開始執行printf函數,相當於printf("%s %s/n",buf,buf),可以看出,輸出應該是相同的buf內的內容,
而此時buf的內容為get_a_day(0)執行後的結果,內容為Sunday,故輸出Sunday Sunday
總結:通過這個小程式的分析可以學到幾點知識
1、調用一個函數時,在所有準備工作做完之後、函數調用開始之前是Sequence Point。比如調用foo(f(), g())時,foo、f()、g()
這三個運算式哪個先求值哪個後求值是Unspecified,但是必須都求值完了才能做最後的函數調用,所以f()和g()的Side Effect按什麼順
序發生不一定,但必定在這些Side Effect全部作用完之後才開始調用foo函數。
2、要注意函數的傳回值,若兩個函數返回的是同一個地址指標,那指的是同一塊記憶體,內容相同。