本文的12個c語言面試題,涉及指標、程序、運算、結構體、函式、記憶體,而且有趣,看看你能做出幾個!
問:請找出下面**裡的問題
#include答:上面**裡的問題在於函式int main(void)
gets()
的使用,這個函式從stdin
接收乙個字串而不檢查它所複製的快取的容積,這可能會導致快取溢位。這裡推薦使用標準函式fgets()
代替。
問:下面是乙個簡單的密碼保護功能,你能在不知道密碼的情況下將其破解嗎?
#include答:破解上述加密的關鍵在於利用攻破int main(int argc, char *argv)
if(flag)
else
return
0; }
strcpy()
函式的漏洞。所以使用者在向「passwd
」快取輸入隨機密碼的時候並沒有提前檢查「passwd
」的容量是否足夠。所以,如果使用者輸入乙個足夠造成快取溢位並且重寫「flag
」變數預設值所存在位置的記憶體的長「密碼」,即使這個密碼無法通過驗證,flag驗證位也變成了非零,也就可以獲得被保護的資料了。例如:
$ ./psswd aaaaaaaaaaaaa雖然上面的密碼並不正確,但我們仍然可以通過快取溢位繞開密碼安全保護。password cracked
要避免這樣的問題,建議使用strncpy()
函式。
作者注:最近的編譯器會在內部檢測棧溢位的可能,所以這樣往棧裡儲存變數很難出現棧溢位。在我的gcc
裡預設就是這樣,所以我不得不使用編譯命令『-fno-stack-protector
』來實現上述方案。
問:下面的**能 編譯通過嗎?如果能,它有什麼潛在的問題嗎?
#include答:因為void main(void)
else
return;
}
main()
方法的返回型別,這段**的錯誤在大多數編譯器裡會被當作警告。main()
的返回型別應該是「int
」而不是「void
」。因為「int
」返回型別會讓程式返回狀態值。這點非常重要,特別當程式是作為依賴於程式成功執行的指令碼的一部分執行時。
問:下面的**會導致記憶體洩漏嗎?
#include答:儘管上面的**並沒有釋放分配給「void main(void)
else
return;
}
ptr
」的記憶體,但並不會在程式退出後導致記憶體洩漏。在程式結束後,所有這個程式分配的記憶體都會自動被處理掉。但如果上面的**處於乙個「while
迴圈」中,那將會導致嚴重的記憶體洩漏問題!
問:下面的程式會在使用者輸入』freeze
『的時候出問題,而』zebra
『則不會,為什麼?
#include答:這裡的問題在於,**會(通過增加「int main(int argc, char *argv)
else
if(argc == 1)
else
if(*ptr == 'z')
free(ptr);
} return
0; }
ptr
」)修改while
迴圈裡「ptr
」儲存的位址。當輸入「zebra
」時,while
迴圈會在執行前被終止,因此傳給free()
的變數就是傳給malloc()
的位址。但在「freeze
」時,「ptr
」儲存的位址會在while
迴圈裡被修改,因此導致傳給free()
的位址出錯,也就導致了seg-fault
或者崩潰。
問:在下面的**中,atexit()
並沒有被呼叫,為什麼?
#include答:這是因為void func(void)
int main(void)
_exit()
函式的使用,該函式並沒有呼叫atexit()
等函式清理。如果使用atexit()
就應當使用exit()
或者「return
」與之相配合。
問:你能設計乙個能接受任何型別的引數並返回interger
(整數)結果的函式嗎?
答:如下:
int func(void *ptr)如果這個函式的引數超過乙個,那麼這個函式應該由乙個結構體來呼叫,這個結構體可以由需要傳遞引數來填充。
問:下面的操作會輸出什麼?為什麼?
#include答:輸出結果應該是這樣:int main(void)
[l]因為「[i]
++
」和「*
」的優先權一樣,所以「*ptr++
」相當於「*(ptr++)
」。即應該先執行ptr++
,然後才是*ptr
,所以操作結果是「l
」。第二個結果是「i
」。
問:下面的**段有錯,你能指出來嗎?
#include答:這是因為,通過int main(void)
*ptr = 『t』
,會改變記憶體中**段(唯讀**)「linux」的第乙個字母。這個操作是無效的,因此會造成seg-fault
或者崩潰。
問:你能寫出乙個在執行時改變自己程序名的程式嗎?
答:參見下面這段**:
#include問:下面**有問題嗎?如果有,該怎麼修改?int main(int argc, char *argv)
#include答:儘管上面的程式有時候能夠正常執行,但是在「int* inc(int val)
int main(void)
inc()
」中存在嚴重的漏洞。這個函式返回本地變數的位址。因為本地變數的生命週期就是「inc()
」的生命週期,所以在inc
結束後,使用本地變數會發生不好的結果。這可以通過將main()
中變數「a
」的位址來避免,這樣以後還可以修改這個位址儲存的值。
問:下面**會輸出什麼?
#include答:輸出結果是:int main(void)
110..40..60這是因為c語言裡函式的引數預設是從右往左處理的,輸出時是從左往右。
12個有趣面試題(C語言)
1.gets 函式 includeint main int argc,char argv 答 上面 裡的問題在於函式gets 的使用,這個函式從stdin接收乙個字串而不檢查它所複製的快取的容積,這可能會導致快取溢位。這裡推薦使用標準函式fgets 代替。修改 gets buff 替換 fgets ...
12個有趣的C語言面試題
摘要 12個c語言面試題,涉及指標 程序 運算 結構體 函式 記憶體,看看你能做出幾個!1.gets 函式 問 請找出下面 裡的問題 include int main void 2.strcpy 函式 問 下面是乙個簡單的密碼保護功能,你能在不知道密碼的情況下將其破解嗎?include int ma...
12個有趣的C語言面試題
發表於 09 06 09 15 csdn 王然面試題c 摘要 12個c語言面試題,涉及指標 程序 運算 結構體 函式 記憶體,看看你能做出幾個!1.gets 函式 問 請找出下面 裡的問題 include int main void 2.strcpy 函式 問 下面是乙個簡單的密碼保護功能,你能在不...