如何使用斷言功能
回答
斷言沒有返回,如果參數爲假,則程序終止。斷言旨在用於不可能發生的情況......但是,如果你錯誤地假設或者這樣,你會檢查。
assert(expression);
什麼斷言確實是評估表達,如果它的計算結果進行比較,以0 /假,程序終止。
不要在用戶輸入中使用斷言。 Assert旨在通過崩潰程序來捕獲邏輯錯誤(通過在斷言失敗時調用中止),並且用戶輸入不會導致程序崩潰。
但要回答你的問題,如果NDEBUG被定義,然後assert什麼都不做。這可能是您的程序未按預期崩潰的原因。
實際上,它的目的是通過在故障點_terminating_你的程序來捕獲邏輯錯誤,而不是你的程序_crashing_在覆蓋你的音樂文件夾中的所有字節 –
之後潛在很遠,即我不會調用什麼'assert'會「崩潰「 –
@LightnessRacesinOrbit - 對我來說,」崩潰「是當一個程序終止時,一個信號使程序掉核。這正是'assert'所做的。 'assert'的SIGABRT和'malloc'或'free'的SIGABRT在進入恐慌模式時有什麼區別?您使用'assert'來檢測程序員錯誤,而不是用戶錯誤。對於程序員來說,核心轉儲是一個很好的錯誤信息。對於用戶來說,核心轉儲是一個非常糟糕的錯誤消息。 –
你可以假設斷言聲明爲以下幾點:
/*!
* Immediately crash the program if assumption is proven invalid.
*/
void assert (bool assumption);
如果你「知道」一個變量t
絕不會超出範圍[1,10],因爲你寫的代碼,並有沒有辦法你的代碼可以產生任何其他值,那麼它是適當的斷言該聲明。
斷言明顯的事情
考慮以下使用斷言:
int t = 9;
assert (9 == t); // A very valid assertion, if a little pedantic.
上面的代碼應該看起來像說明明顯。聲明的表達是(顯然)是真實的,但更重要的是任何其他結果將是瘋狂的。知道t != 9
會清除所有關於C++如何工作的假設,計算機如何執行數學和存儲值,無論我們是否存在,或者意識是否僅僅是由許多惡化的電子形成的錯覺...
但這就是斷言的價值。
即使這樣的電腦是爲所有實際目的100%確定性,「瘋狂」的事情做發生。這也不是罕見的。實際上,我們在我們的代碼中明確地寫出斷言來檢測這些情況,並給我們一個機會來找出發生了什麼。 這裏考慮幾個真實世界的瘋狂行爲原因。「瘋狂」 的行爲
原因
你的斷言應該防範此類錯誤的...
不正確的線程同步。
int t; // Thread 1 t = 9; assert(t == 9); // Thread 2 t = 3; assert(t == 3);
內存管理不好。
class X { void sayHello() { assert(this != NULL); // An object that does not exist cannot say hello. std::cout << "Hello?" << std::endl; } }; // Without the assertion, this code would actually run! X* x = NULL; x->sayHello();
堆棧(或堆)腐敗。
(合理的例子見Stack corruption in C++。)
行爲是不方便,但不是瘋了:
雖然這可能會大大改變你的程序的執行路徑,這些東西都是不合適的斷言。拋出異常,打印錯誤,很好地關閉程序,並負責任地清理程序的資源。 不要斷言這些「失敗」!
用戶輸入了一些荒謬的東西。
int t; scanf("%d", &t); assert (0 <= t <= 10); // What, are you friends with this user? // You're going to let him crash your program?
某些I/O設備發生故障。
int s = socket(); // blah blah connect blah blah char buffer[64]; int bytes_received = recv(s, buffer, 64, NULL); assert (bytes_received > 0); // Do you know how hard it is to send a packet // from Estonia to the US?!
這個列表是不完整的,但它應該給你如何(以及如何不)應用的斷言更廣泛的指南。
妥善解決你的問題是封裝在一個函數scanf()
功能,知道它在做什麼:
int AskNumberOfWidgetFrobs() {
int count = 0;
for(;;) // Until we get a valid number
scanf("%d", &count);
if (count > 0 && count <= 10) {
return count;
} else {
printf("%d is not a valid number of WidgetFrobs\n", count);
}
}
}
這是我希望這樣回答的:
Specifiy
#include <assert.h>
在源文件開始的單獨行中。
現在,只要bool不正確,您就可以使用assert(bool)來終止程序。
(其他的答案是這樣一個問題:「如何使用斷言正確」)
- 1. 使用Codeception,Symfony2功能測試服務如何添加斷言?
- 2. 如何用新的斷言功能擴展QUnit?
- 3. 斷言,打印陣列功能
- 4. 「minitest/spec」中有哪些斷言功能?
- 5. 調試斷言在cout功能失敗
- 6. 斷言失敗,CopyTo從功能(C++)
- 7. 需要類型斷言的功能
- 8. 斷言性能
- 9. 如何使用JMeter「斷言」和「如果」?
- 10. 如何用誓言測試此功能?
- 11. 如何在塊中使用斷言?
- 12. 如何使用Makefile關閉斷言
- 13. 如何使用Jasmine斷言異常?
- 14. 如何在lex中使用lookbehind斷言?
- 15. 如何使用流體斷言.ShouldBeNull()
- 16. 如何在android中使用斷言?
- 17. C# - ;使用斷言
- 18. 使用斷言使用JUnit
- 19. 如何在功能中使用功能
- 20. 寫調試構建只斷言功能忽略副作用
- 21. Shouldly斷言庫如何知道斷言適用的表達式?
- 22. 什麼是所有可能的斷言功能?
- 23. 功能中斷
- 24. 此功能使用什麼語言?
- 25. 如何在java類中使用struts多語言功能
- 26. 如何使用PHP語言環境功能
- 27. 如何實現一種功能語言
- 28. 從rspec中斷言斷言與斷言
- 29. 序言,如何讀值親功能在其他功能
- 30. 如何從QAction斷開功能?
這在技術上是一個宏,不是一個函數。 – chris
第一次檢查用戶輸入是否爲1,另一次檢查範圍是否在1到10之間 – MimiEAM
@MimiEAM,'scanf'的返回值是成功輸入的項目數。 – chris