變量的初始化與使用C語言程序注釋,c - (為什么)使用未初始化的變量未定義行為?...

C標準為編譯器提供了很大的優勢來執行優化。 如果您假設一個簡單的程序模型,其中未初始化的內存被設置為某個隨機位模式,并且所有操作都按照它們的寫入順序執行,那么這些優化的后果可能會令人驚訝。

注意:以下示例僅有效,因為x從未使用其地址,因此它是“類似寄存器”。 如果x = - x的類型具有陷阱表示,它們也將有效; 這對于無符號類型來說很少見(它需要“浪費”至少一位存儲空間,并且必須記錄在案),而-x則不可能。如果x有簽名類型,那么實現可以定義不是 - (2n-1-1)和2n-1-1之間的數字作為陷阱表示。 見Jens Gustedt的回答。

編譯器嘗試將寄存器分配給變量,因為寄存器比內存快。 由于程序可能使用比處理器具有寄存器更多的變量,因此編譯器執行寄存器分配,這導致在不同時間使用相同寄存器的不同變量。 考慮程序片段

unsigned x, y, z; /* 0 */

y = 0; /* 1 */

z = 4; /* 2 */

x = - x; /* 3 */

y = y + z; /* 4 */

x = y + 1; /* 5 */

當評估第3行時,x = - x尚未初始化,因此(編譯器的原因)第3行必須是由于編譯器不夠聰明的其他條件而不能發生的某種僥幸。 由于在第4行之后未使用-x,并且在第5行之前未使用x,因此可以對兩個變量使用相同的寄存器。 所以這個小程序編譯成寄存器上的以下操作:

r1 = 0;

r0 = 4;

r0 = - r0;

r1 += r0;

r0 = r1;

最終值x = - x是最終值-x,最終值x是最終值x.這些值是x = -3和y = -4,而不是5和4,如果x = some_value()已經發生 正確初始化。

有關更詳細的示例,請考慮以下代碼片段:

unsigned i, x;

for (i = 0; i < 10; i++) {

x = (condition() ? some_value() : -x);

}

假設編譯器檢測到x = - x沒有副作用。 由于-x不修改x,編譯器知道第一次循環運行不可能訪問x,因為它尚未初始化。 因此,循環體的第一次執行相當于x = some_value(),無需測試條件。 編譯器可以編譯此代碼,就像您編寫的那樣

unsigned i, x;

i = 0; /* if some_value() uses i */

x = some_value();

for (i = 1; i < 10; i++) {

x = (condition() ? some_value() : -x);

}

這可以在編譯器內建模的方式是考慮依賴于x = - x的任何值都具有方便的值,只要-x未初始化即可。 因為未初始化變量未定義時的行為,而不是僅具有未指定值的變量,編譯器不需要跟蹤任何方便值之間的任何特殊數學關系。 因此編譯器可以用這種方式分析上面的代碼:

在第一次循環迭代期間,x = - x在評估-x時未初始化。

x = - x具有未定義的行為,因此它的值是任何方便的。

優化規則? 價值:價值適用,所以這段代碼可以簡化為; 值。

當遇到問題中的代碼時,同一個編譯器會分析當評估x = - x時,-x的值是方便的。 因此,可以優化分配。

我沒有找到一個行為如上所述的編譯器的例子,但它是優秀的編譯器試圖做的優化。 遇到一個我不會感到驚訝。 這是程序崩潰的編譯器的一個不太合理的例子。 (如果在某種高級調試模式下編譯程序,可能不會令人難以置信。)

這個假設的編譯器將每個變量映射到不同的內存頁面并設置頁面屬性,以便從未初始化的變量讀取會導致調用調試器的處理器陷阱。 首先對變量賦值,確保其內存頁面正常映射。 此編譯器不會嘗試執行任何高級優化 - 它處于調試模式,旨在輕松定位諸如未初始化變量之類的錯誤。 當評估x = - x時,右側會導致陷阱并且調試器將啟動。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/443517.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/443517.shtml
英文地址,請注明出處:http://en.pswp.cn/news/443517.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

三羊獻瑞c語言編程入門,藍橋杯-三羊獻瑞,

藍橋杯-三羊獻瑞&#xff0c;更多精彩文章請關注公眾號『大海的BLOG』問題觀察下面的加法算式&#xff1a;祥 瑞 生 輝 三 羊 獻 瑞----------------三 羊 生 瑞 氣其中&#xff0c;相同的漢字代表相同的數字&#xff0c;不同的漢字代表不同的數字&#xff0c;‘三’和‘祥’不…

Struts2.3接收post方式提交的表單參數的方式

一&#xff1a;方式一&#xff1a;通過request來獲取&#xff0c;首先讓action實現ServletRequestAware接口&#xff0c;然后通過request來獲取提交的參數&#xff0c;代碼如下: package cn.gov.csrc.flight.action;import java.util.HashMap; import java.util.List; import j…

倒果汁c語言,水果榨汁補維生素C?這些補維生素的錯誤別再犯了

原標題&#xff1a;水果榨汁補維生素C&#xff1f;這些補維生素的錯誤別再犯了蔬菜和水果作為維生素C、礦物質和植物纖維的重要來源&#xff0c;是每天餐桌上都要出現的食物&#xff0c;一旦水果蔬菜吃不夠&#xff0c;身體就會開始找你麻煩。在處理蔬菜水果的時候&#xff0c;…

dos和linux有關系嗎,DOS和Linux近年來的發展比較

大家都聽說過Linux操作系統吧&#xff01;Linux誕生于20世紀的90年代初&#xff0c;于90年代末開始出名并在許多人中開始了實際使用。著名的“開放源代碼”運動更是使新的Linux程序不斷出現&#xff0c;使Linux得到了進一步的發展&#xff0c;尤其是在服務器領域得到了較大的應…

c語言中二維數組的結構體,怎么才能把結構體里面的二維數組打印出來?

該樓層疑似違規已被系統折疊 隱藏此樓查看此樓萌新一位&#xff0c;學到結構體在做作業&#xff0c;遇到了這個問題。求提示出現這樣的報錯&#xff1a;[Error] cannot convert char (*)[20] to char* for argument 5 to void HeroShow(int, int, char*, char*, char*, char*)#…

android中資源文件的兩種訪問方式,Android_Android學習筆記-保存文件(Saving Files),Android設備有兩種文件存儲區域 - phpStudy...

Android學習筆記-保存文件(Saving Files)Android設備有兩種文件存儲區域:內部存儲和外部存儲 ("internal" and "external" storage)。這名字來自早期Android&#xff0c;那時大多數Android設備提供兩種存儲方式:內置的非易失的內存(內部存儲)和可移動的存儲…

Struts2.3,s:iterator,c:forEach遍歷map中的list集合

一&#xff1a;首先是<s:iterator></s:iterator>遍歷map中的list集合&#xff0c;代碼如下&#xff1a; 1.首先是后臺代碼&#xff0c;包括定義map和給map中賦值&#xff0c;代碼如下&#xff1a; package cn.gov.csrc.cms.action;import java.util.HashMap; impo…

android 判斷對象,Android網絡判斷知識小結

Android中判斷當前網絡是否可用應用場景&#xff1a;實現判斷當前網絡是否可用當前有可用網絡&#xff0c;如下圖&#xff1a;當前沒有可用網絡&#xff0c;如下圖&#xff1a;實現步驟&#xff1a;1、獲取ConnectivityManager對象Context context activity.getApplicationCon…

android fragment動畫,Fragment 的過場動畫

Fragment 的過場動畫Android,Fragment,動畫2018.08.03在 Android 開發中&#xff0c;有些應用對頁面的過場動畫要求比較高&#xff0c;他們中期望給用戶提供一個良好的用戶體驗。適當的過場動畫可以減少用戶在頁面加載時期等待的焦慮&#xff0c;因為讓他們看一個動畫&#xff…

android 聯系人批量插入,GitHub - Atinerlengs/InsertDemo: android 簡單的批量插入通話記錄、聯系人、短信demo...

[toc]批量插入批量插入通話記錄下面是添加通話數據的代碼&#xff0c;我們自己去構造Tb_calllogs數據&#xff0c;里面可以添加通話記錄數據字段&#xff0c;由于是個簡單的demo&#xff0c;所以只加了number、callType、date、callDuration。/*** 添加通話數據** throws Remot…

html頁面按鈕刪除一條數據庫,需要添加一個刪除按鈕到一個HTML表格從數據庫中刪除記錄與消息...

IDNameCodeActiveEdit<?php foreach($nurseries->result() as $nursery) { ?><?php echo $nursery->id; ?><?php echo $nursery->name; ?><?php echo $nursery->code; ?><?php echo set_bool($nursery->active); ?><…

EL表達式, JSTL, 獲取map集合中key的value

序言&#xff1a;今天在項目中使用了map存儲list和普通對象&#xff0c;但是在jsp中顯示的時候出來問題&#xff0c;后經查閱&#xff0c;終于解決&#xff0c;現在記錄一下&#xff0c;以便以后查閱&#xff1a; 一&#xff1a;后臺代碼如下&#xff1a; package cn.gov.csrc…

html選擇器是什么,CSS3選擇器是什么?

首先我們來看一下displaynone的意思是什么&#xff1f;display:none的意思&#xff1a;隱藏元素并脫離文檔&#xff0c;流就是隱藏該區域&#xff0c;不占實際空間&#xff0c;但對后臺來說真實存在&#xff0c;可以獲取被隱藏的元素簡單的來說就是將元素設置為none的時候既不會…

零基礎學計算機408,又一所重點大學改考408!21計算機考研會全面408嗎?

【北京工業大學】于7月17日發布《關于北京工業大學2021年全國碩士研究生招生考試部分考試科目及考試大綱調整的通知》&#xff0c;要點如下&#xff1a;文法學部0401教育學專業課改考 311統教育學信息學部計算機學院0812計算機科學與技術0839網絡空間安全0854電子信息 (專業學位…

國貿專業要考計算機二級,國貿專業考計算機二級有沒有必要

類似問題答案我是自動化專業的學生&#xff0c;大一的時候有沒有必要考計算機二級證書計算機二級 雖然不是很重要 但是考了也是有好處的 自動化的跟計算機聯系非常大 二級證不怎么重要 但是C語言很重要 對于你們 希望你還是去考個二級作為學習建筑類專業的學生,如果考試計算機二…

edge如何導入html文件收藏夾,edge瀏覽器收藏夾如何導入?edge瀏覽器收藏夾導入方法...

在使用瀏覽器的時候需要用戶進行多方便的導入和使用&#xff0c;這樣在數據共享和傳遞的時候才會更加的方便&#xff0c;那么這款軟件要如何操作使用呢&#xff0c;有興趣的用戶可以使用手機快速申請使用&#xff0c;幫助用戶的生活&#xff0c;讓用戶的生活更加的便捷&#xf…

中職生計算機專業600分,來了!超全盤點高職分類中500-600分及以上的高中生能報的專業和院校名單!...

福建高職分類考試志愿填報4月27日開始&#xff0c;招生計劃不斷更新中關注【福建高考】&#xff0c;免費使用志愿填報工具參加高職分類的同學們志愿填報在即&#xff0c;你定好目標了嗎&#xff1f;本期&#xff0c;小編為大家盤點高職分類各分段的高中生能報哪些專業和大學~一…

Oracle中通過:觸發器,存儲過程,Function調用實現解析Clob字段類型中存儲的xml字符串...

摘要&#xff1a;最近項目中用到了存儲過程&#xff0c;觸發器&#xff0c;Function&#xff0c;由于以前沒怎么用過&#xff0c;所以查資料&#xff0c;請教同事&#xff0c;最后總算是把問題解決了&#xff0c;問題是這樣的&#xff0c;數據庫中有三張表一張是存放從遠程服務…

plc采用計算機結構如何理解,PLC的基本結構

plc實質是一種專用于工業控制的計算機&#xff0c;其硬件結構基本上與微型計算機相同&#xff0e;a. 中央處理單元(CPU)中央處理單元(CPU)是PLC的控制中樞。它按照PLC系統程序賦予的功能接收并存儲從編程器鍵入的用戶程序和數據&#xff1b;檢查電源、存儲器、I/O以及警戒定時器…

華為手機怎么用計算機玩隱藏空間,玩法 | 華為手機這五個隱藏功能,用過的都說好!...

原標題&#xff1a;玩法 | 華為手機這五個隱藏功能&#xff0c;用過的都說好&#xff01;歡迎轉載&#xff0c;請注明出處&#xff0c;抄襲必究&#xff01;近年來國產手機都很爭氣&#xff0c;華為、小米、OPPO、vivo都迅速的成長起來&#xff0c;讓大家告別了瘋搶蘋果的時代。…