最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

關(guān)于C/C++中的side effect(負(fù)效應(yīng))和sequence point(序列點(diǎn))

 更新時(shí)間:2013年10月03日 09:55:07   作者:  
不知你在寫code時(shí)是否遇到這樣的問題?int i = 3; int x = (++i) + (++i) + (++i); 問x值為多少?進(jìn)行各種理論分析,并在編譯器上實(shí)踐,然而可能發(fā)現(xiàn)最終的結(jié)果是不正確的,也是不穩(wěn)定的,不同的編譯器可能會產(chǎn)生不同的結(jié)果。這讓人很頭疼

不知你在寫code時(shí)是否遇到這樣的問題?int i = 3; int x = (++i) + (++i) + (++i); 問x值為多少?進(jìn)行各種理論分析,并在編譯器上實(shí)踐,然而可能發(fā)現(xiàn)最終的結(jié)果是不正確的,也是不穩(wěn)定的,不同的編譯器可能會產(chǎn)生不同的結(jié)果。這讓人很頭疼。結(jié)果到底是啥呢?對于此題的答案,一句話,Theresult is undefined! 詳細(xì)解釋待我慢慢說來。

大家知道,通常而言,我們寫的計(jì)算機(jī)程序都是從上到下,從左到右依次執(zhí)行。然而,我只是說通常,因?yàn)樵诰幾g的過程中,compiler并不僅僅是把source code翻譯成binary code就算了,這個(gè)過程里面可能還會對代碼進(jìn)行優(yōu)化,這種優(yōu)化可能帶來的結(jié)果是:代碼或者表達(dá)式evaluation的順序可能發(fā)生變化。這可是一個(gè)非常嚴(yán)重的問題,當(dāng)某個(gè)表達(dá)式帶有side-effect(比如改變了一個(gè)變量的值),那么它的執(zhí)行順序直接影響到了程序執(zhí)行的結(jié)果。

為了保證程序執(zhí)行具有確定性的結(jié)果,C++標(biāo)準(zhǔn)引入Sequence Point這個(gè)概念,按照ISO/IEC的定義:

At certain specified points in the execution sequence called sequence points. All side effects of previous evaluations shall be complete and no side effects of subsequent evaluations shall have taken place.

簡而言之,Sequence Point就是這么一個(gè)位置,在它之前所有的side effect已經(jīng)發(fā)生,在它之后的所有side effect仍未開始,而兩個(gè)Sequence Point之間所有的表達(dá)式或者代碼執(zhí)行的順序是未定義的!

而C++標(biāo)準(zhǔn)又進(jìn)一步規(guī)定了Sequence Point出現(xiàn)的5種情況:

1、At the end of a full expression
在一個(gè)完整的表達(dá)式末尾是Sequence Point,所謂完整的表達(dá)式是指這個(gè)表達(dá)式不是另外一個(gè)表達(dá)式的一部分。所以如果有f(); g();這樣兩條語句,f()和g()是兩個(gè)完整的表達(dá)式,f()的Side Effect必定在g()之前發(fā)生。

2、After the evaluation of all function arguments in a function call and before execution of any expressions in the function body
調(diào)用一個(gè)函數(shù)時(shí),在所有準(zhǔn)備工作做完之后、函數(shù)調(diào)用開始之前是Sequence Point。比如調(diào)用foo(f(), g())時(shí),foo、f()、g()這三個(gè)表達(dá)式哪個(gè)先求值哪個(gè)后求值是Unspecified,但是必須都求值完了才能做最后的函數(shù)調(diào)用,所以f()和g()的Side Effect按什么順序發(fā)生不一定,但必定在這些Side Effect全部作用完之后才開始調(diào)用foo函數(shù)。

3、After copying of a returned value and before execution of any expressions outside the function
函數(shù)即將返回時(shí)是Sequence Point,因?yàn)楹瘮?shù)返回時(shí)必然會結(jié)束掉一個(gè)完整的表達(dá)式。

4、After evaluation of the first expression in a&&b,  a||b,  a?b:c,  or  a,b
條件運(yùn)算符?:、逗號運(yùn)算符、邏輯與&&、邏輯或||的第一個(gè)操作數(shù)求值之后是Sequence Point。如條件運(yùn)算符和逗號運(yùn)算符,條件運(yùn)算符要根據(jù)表達(dá)式1的值是否為真決定下一步求表達(dá)式2還是表達(dá)式3的值,如果決定求表達(dá)式2的值,表達(dá)式3就不會被求值了,反之也一樣,逗號運(yùn)算符也是這樣,表達(dá)式1求值結(jié)束才繼續(xù)求表達(dá)式2的值。

5、After the initialization of each base and member in the constructor initialization list
在一個(gè)完整的聲明末尾是Sequence Point,所謂完整的聲明是指這個(gè)聲明不是另外一個(gè)聲明的一部分。比如聲明int a[10], b[20];,在a[10]末尾是Sequence Point,在b[20]末尾也是。

經(jīng)過以上說明,大家已有所了解,現(xiàn)在回到我們的題目:int x = (++i) + (++i) + (++i); 整個(gè)的語句里面,只有1個(gè)Sequence Point,也就是語句的結(jié)束點(diǎn),對于右邊表達(dá)式的計(jì)算順序沒有任何的規(guī)定,顯然,各種編譯器都可以按照他們覺得“舒服”的方式來進(jìn)行計(jì)算,這樣的代碼,如果只要求在特定的平臺或者編譯器運(yùn)行,那么帶來的可能只是可讀性差的問題,但如果考慮跨平臺或者編譯器的情況,那么就是完完全全的錯(cuò)誤!

另外,需要特別注意的是,對于賦值號(assignment operator),C++也沒有把它定義成Sequence Point,也就說這樣的語句:buffer[i] = i++;同樣是undefined的,因?yàn)?,對于等號左右兩邊的表達(dá)式運(yùn)算順序,你并不能有任何的假定。

相關(guān)文章

  • C++ string替換指定字符實(shí)例代碼

    C++ string替換指定字符實(shí)例代碼

    這篇文章主要給大家介紹了關(guān)于C++ string替換指定字符的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對大家學(xué)習(xí)或者使用C++具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面來一起學(xué)習(xí)學(xué)習(xí)吧
    2019-11-11
  • 使用OpenGL繪制Bezier曲線

    使用OpenGL繪制Bezier曲線

    這篇文章主要為大家詳細(xì)介紹了使用OpenGL繪制Bezier曲線的方法,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2020-04-04
  • C++實(shí)現(xiàn)LeetCode(154.尋找旋轉(zhuǎn)有序數(shù)組的最小值之二)

    C++實(shí)現(xiàn)LeetCode(154.尋找旋轉(zhuǎn)有序數(shù)組的最小值之二)

    這篇文章主要介紹了C++實(shí)現(xiàn)LeetCode(154.尋找旋轉(zhuǎn)有序數(shù)組的最小值之二),本篇文章通過簡要的案例,講解了該項(xiàng)技術(shù)的了解與使用,以下就是詳細(xì)內(nèi)容,需要的朋友可以參考下
    2021-07-07
  • opencv求解區(qū)域的內(nèi)接矩形

    opencv求解區(qū)域的內(nèi)接矩形

    這篇文章主要為大家詳細(xì)介紹了opencv求解區(qū)域的內(nèi)接矩形,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2020-07-07
  • 詳解C++中的一維數(shù)組和二維數(shù)組

    詳解C++中的一維數(shù)組和二維數(shù)組

    這篇文章主要介紹了詳解C++中的一維數(shù)組和二維數(shù)組,是C語言入門學(xué)習(xí)中的基礎(chǔ)知識,需要的朋友可以參考下
    2015-09-09
  • VC++ 獲取系統(tǒng)時(shí)間的方法匯總

    VC++ 獲取系統(tǒng)時(shí)間的方法匯總

    本文給大家匯總介紹了5種VC++中獲取系統(tǒng)時(shí)間的方法,十分的簡單實(shí)用,有需要的小伙伴可以參考下。
    2015-07-07
  • C++數(shù)據(jù)結(jié)構(gòu)紅黑樹全面分析

    C++數(shù)據(jù)結(jié)構(gòu)紅黑樹全面分析

    今天的這一篇博客,我要跟大家介紹二叉搜索樹中的另一顆樹——紅黑樹,它主要是通過控制顏色來控制自身的平衡,但它的平衡沒有AVL樹的平衡那么嚴(yán)格
    2022-02-02
  • C++超詳細(xì)講解模板的使用

    C++超詳細(xì)講解模板的使用

    這篇文章主要介紹了C++中模板(Template)的詳解及其作用介紹,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2022-06-06
  • Qt編寫地圖之實(shí)現(xiàn)經(jīng)緯度坐標(biāo)糾偏

    Qt編寫地圖之實(shí)現(xiàn)經(jīng)緯度坐標(biāo)糾偏

    地圖應(yīng)用中都涉及到一個(gè)問題就是坐標(biāo)糾偏的問題,這個(gè)問題的是因?yàn)楦鶕?jù)地方規(guī)則保密性要求不允許地圖廠商使用標(biāo)準(zhǔn)的GPS坐標(biāo),而是要用國家定義的偏移標(biāo)準(zhǔn)。本文將詳細(xì)講解如何在Qt中實(shí)現(xiàn)經(jīng)緯度坐標(biāo)糾偏,需要的可以參考一下
    2022-03-03
  • C語言實(shí)現(xiàn)貪吃蛇游戲設(shè)計(jì)

    C語言實(shí)現(xiàn)貪吃蛇游戲設(shè)計(jì)

    這篇文章主要為大家詳細(xì)介紹了C語言實(shí)現(xiàn)貪吃蛇游戲設(shè)計(jì),文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2020-07-07

最新評論

玛纳斯县| 昌吉市| 读书| 石景山区| 神池县| 宜丰县| 延津县| 廊坊市| 长寿区| 台北县| 禄丰县| 南宁市| 交口县| 孝昌县| 颍上县| 大关县| 金溪县| 黄山市| 寿阳县| 珲春市| 原阳县| 普宁市| 清水县| 靖安县| 涟水县| 富平县| 五莲县| 北流市| 建瓯市| 司法| 于都县| 柳江县| 海宁市| 扶沟县| 资源县| 杂多县| 孟村| 三江| 临沧市| 廊坊市| 余干县|