2011-01-21 27 views
42

這兩個語句在函數內部有區別嗎?返回語句中顯着的結果是括號嗎?

bool returnValue = true; 

//Code that does something 

return(returnValue); 

這個?

bool returnValue = true; 

//Code 

return returnValue; 

前者的圓括號爲returnValue

+10

準備一些徽章。奇怪的是,這些問題總是*獲得最多的觀點。 –

+2

歡迎來到Stack Overflow,Jose。請注意我對你的問題所做的修改。它特別提到了這兩個代碼塊之間的變化,這可以讓讀者免於使用代碼玩[找出差異](http://www.spotthedifference.com/)的煩惱。它還可以幫助人們識別差異是有意的,而不僅僅是一個簡單的錯字(比如'boo')。 –

+0

感謝羅布,你成功抓住了這個問題的精神。在本質上,我想知道編譯器是否做了任何特殊的事情(比如試圖首先評估表達式)或者它是否忽略了它。 –

回答

63

C++ 14增加了一個邊緣如果返回值附近的括號可能會改變語義。這段代碼顯示了兩個正在聲明的函數。唯一的區別是圍繞返回值的括號。

int var1 = 42; 
decltype(auto) func1() { return var1; } // return type is int, same as decltype(var1) 
decltype(auto) func1() { return(var1); } // return type is int&, same as decltype((var1)) 

在第一func1返回一個int和在第二個func1返回一個int&語義的差異直接與周圍的圓括號有關。

在C++ 11中引入了其最新形式的auto說明符。在C++ Language Spec它被描述爲:

指定正在被聲明將是可變的類型自動 從其初始推斷。對於函數,指定該返回類型是尾隨 返回類型或將被從它的返回語句推導出(因爲C++ 14)

除了C++ 11引入,其在所描述的decltypeC++ Language Spec

檢查實體的聲明類型或查詢表達式的返回類型。

[剪斷]

  1. 如果參數是任一的對象/功能的unparenthesised名稱,或者是其成員訪問表達式(object.member或指針 - >部件),則decltype指定此表達式指定的實體的聲明類型。

  2. 如果參數是類型T的任何其他表達,然後

    a)如表達式的值類是x值,則decltype指定Ť& &

    b)如的值類表達左值,則decltype指定Ť&

    c)中,否則decltype指定Ť

[剪斷]

注意,如果一個對象的名稱被parenthesised,它成爲一個左值表達,從而decltype(ARG)和decltype((ARG))通常是不同的類型。

在C++ 14中,函數返回類型允許使用decltype(auto)。原來的例子是與括號的語義差別發揮作用的地方。重溫原始例子:

int var1 = 42; 
decltype(auto) func1() { return var1; } // return type is int, same as decltype(var1) 
decltype(auto) func1() { return(var1); } // return type is int&, same as decltype((var1)) 

decltype(auto)允許在函數尾隨返回類型以從上return語句的實體/表達來推斷。在第一個版本中,return var1;與返回類型decltype(var1)(上述規則1的返回類型爲int)的效果相同,而在第二種情況下,它與decltype((var1))(規則2b的int &返回類型)的效果相同。

圓括號使返回類型int&而不是int,從而在語義上的變化。 故事的道德 - 「不是返回類型上的所有圓括號都是相同的」

+0

沒有括號的return語句仍然是一個左值表達式,對吧?除非在這種情況下它被視爲一個xvalue。你能解釋沒有括號的回報的價值類別嗎? –

+0

return語句返回讀入的表達式,即它從它包含的表達式中捕獲一個右值並返回該值。我們永遠不會返回一個左值。一些編譯器可能有一個與你在這裏給出的描述相匹配的錯誤,也可能出於你在這裏給出的原因,但它不應該是'return(x);'等價於'return&x;',也不是是否有可能導致返回x的值,但是將類型引用爲x。 –

11

是的,一個返回bool,而另一位boo ...


編輯後:

沒有,它們是相同的。

+1

這是我認爲的一個錯字。 –

+0

謝謝你指出。 –

+0

+1爲有趣的答案編輯答案;) – BlackBear

0

沒有區別!

人們用括號如果有涉及到複雜的表達式。

BTW return是一個語句不是一個函數。

+0

更像人們使用圓括號,如果他們是C的新手.. –

5

沒有區別。

一個原因使用括號是,如果你想返回你的例子之前,但在評估的表達,也就沒有理由。請參閱:

Parenthesis surrounding return values

作進一步討論。

+2

即使有一個複雜的表達式,這些括號仍然不會導致不同的行爲。他們只是讓人類的讀者更明顯(主觀上)。 – aschepler

+0

@Karl「如果你想在返回之前評估一個表達式,那麼使用括號的一個原因是」你能舉一個例子嗎? –

+0

@ChrisMiddleton不,因爲這裏的聲明和該線程一樣荒謬。 'return m * x + c'和'return(m * x + c)'或'return((m * x)+ c)'之間沒有任何功能上的區別 - 等等如果你問我,也可以更好或更直觀。 –

2

不,您的代碼沒有區別。

2

我認爲boo是一個錯字,你問是否有

return expr; 

return(expr); 

之間的差異,答案是否定的。

3

AFAIK,沒什麼不同。

在C++中,表達式可以具有以下形式:expr(expr)。所以,後者是一種更多打字的表達方式。有關這方面的更多信息,請參閱a grammar(查找「表達式」)。

+0

大衛,感謝您的鏈接。我在Stroustrup的C++書中有這樣的語法,但是(我猜想出於懶惰)不要那麼看,現在我已經在瀏覽器中加入了書籤,我可以更頻繁地引用它。 –

3

上面例子的括號是多餘的;他們被有效地忽視。

這將是相同的像...

int x = (5); 

這裏的括號被忽略爲好。

+0

嗯,從技術上講,它們不被忽略*,它們對錶達式的值沒有影響。 –

+0

@約翰:*有效*忽略。 :) – James

+3

+1 ...這是唯一的答案,表明括號實際上是*冗餘*,並表明他們的使用有點愚蠢。 –

1

都能跟得上有兩者之間沒有任何區別,雖然也可以括號,如果它使表達式易於閱讀和明確的。

+0

...但它永遠不會。爲什麼呢?什麼是難以閱讀的關於一個不言辭的表達?添加括號對我來說看起來很混亂。至於看起來更清楚,人們是否認爲'return'是一個貪婪的操作符,並且'return m * x + c'可能會返回'm'並丟棄其餘的或者什麼? –

1

你濫用放緩編譯器!

圓括號的存在不僅延緩了預處理階段,而且還產生了更復雜的抽象語法樹:更多內存,更多計算。


從語義的角度來看?它們完全相同。在返回之前,是否有括號或不包括return語句將完全評估表達式。

+4

我的想法確切。通過讓編譯器做不必要的工作來解析無用的混亂,它正在接近宇宙的熱死亡,沒有任何理由。 –

+0

您對比特幣有什麼看法? –

1

它們是相同的。我經常看到括號語法,我總是問使用它的人:爲什麼?沒有人能回答他們爲什麼使用它。

爲了直截了當地總結,圍繞返回表達式的括號被那些不太瞭解類似函數的宏和函數之間的區別,或者對C中的運算符優先級或評估規則的順序感到困惑的人使用。使用括號沒有編碼風格的好處。

因此

return value; 

return (value) 

更正確,因爲後者建議你不太知道你在做什麼:)

-4

兩者在您的情況下都是一樣的。

+0

這個答案是錯的 –

+0

M.M你能解釋一下你的評論嗎? –

+0

如果'a'爲'5',那麼'return a ++;'和'return(a ++);'(這是相同的)將返回特定的'5' –