2011-04-12 57 views
5

不好意思纏着大家,但這一直給我帶來一些痛苦。下面的代碼:用sprintf掙扎...有些愚蠢?

char buf[500]; 
sprintf(buf,"D:\\Important\\Calibration\\Results\\model_%i.xml",mEstimatingModelID); 

mEstimatingModelID是一個整數,目前持股價值爲0。

很簡單,但調試表明這種情況正在發生:

0x0795f630 "n\Results\model_0.xml" 

即它缺少字符串的開頭。

任何想法?這很簡單,但我無法弄清楚。

謝謝!

+2

你確定它不是調試器愚弄你?嘗試使用關閉優化的調試版本,或者更輕鬆地輸出「buf」的值。 – 2011-04-12 15:46:46

+2

您何時檢查結果:在此功能中,還是以後的某個時間?你沒有從這個函數返回一個指向「buf」的指針,對嗎?你可能知道這一點,但你不能從函數返回一個指向基於棧的變量的指針;只要函數返回,變量就會變成垃圾。 – 2011-04-12 15:48:26

+2

在Ideone獨立作品 - http://www.ideone.com/wJJ6o,看起來像你的調試器正在玩。 – 2011-04-12 15:53:56

回答

3

在努力使這是一個實際的籠統的回答:這裏有一個類似的錯誤清單:

  • 永遠不要相信你在釋放模式看,已經從堆棧內存分配尤其是局部變量。存在於堆數據中的靜態變量大概是唯一通常是正確的,但即使如此,也不要相信它。 (以上是用戶的情況) 我的經驗是,更新版本的VS具有不太可靠的發佈模式數據(可能是b/c,它們在發佈時優化得多,或者它可能是64bit或其他)

  • 總是確認您正在檢查正確功能中的變量。在一個高級函數中有一個名爲「buf」的變量是非常容易的,該函數中有一些未初始化的垃圾。這很容易與較低子程序/函數中的相同命名變量混淆。

  • 重複檢查緩衝區溢出總是一個好主意。如果你曾經在你的sprintf中使用%s,你的可能會在得到一個緩衝區溢出。

  • 檢查您的類型。 sprintf是非常適應性的,你可以很容易地得到一個非崩潰但奇怪的結果,通過傳遞一個字符串指針,當一個int是預期等

+0

您可能還補充說,儘管MS提供的版本不完全符合C99標準,並且不保證以null結尾的字符串(出於MS最爲人所知的原因),但snprintf()可以很大程度上避免緩衝區溢出問題。 – 2011-04-14 01:37:37

+1

+1表示不信任在調試器中釋放模式下看到的任何人。 – Xeo 2011-04-14 01:39:58