2012-05-10 86 views
5

定義一個浮點變量a,將a轉換爲浮點數&和int &,這是什麼意思?轉換之後,a是自己的參考?爲什麼這兩個結果是不同的?這是什麼意思? (int&)a

#include <iostream> 
using namespace std; 
int 
main(void) 
{ 
    float a = 1.0; 
    cout << (float &)a <<endl; 
    cout << (int &)a << endl; 

    return 0; 
} 


thinkpad ~ # ./a.out 
1 
1065353216 
+0

這是功課嗎? – caskey

回答

14
cout << (float &)a <<endl; 
cout << (int &)a << endl; 

第一個治療在就像是一個浮動的位。第二個將對象看作是一個int。浮法1.0比特恰好是對整數1065353216.

比特它基本上相當於:

float a = 1.0; 
int* b = (int*) &a; 
cout << a << endl; 
cout << *b << endl; 

(int &) a投下到爲整數的參考。換句話說,一個整數引用一個。 (正如我所說,它將a的內容視爲一個整數。)

編輯:我現在正在四處看看,看看這是否有效。我懷疑它不是。這取決於類型小於或等於實際大小。

+4

這很有趣。我不知道鑄造到一個參考類型實際上等同於執行重新解釋演員。 –

+0

@OliCharlesworth我無法分辨你是否認真或諷刺,所以請詳細說明你是否認真。 (我不確定這是否有效,在此之前,我從來沒有看到一個演員指向一個不相關的類型,我試圖從標準中搜索任何東西,但沒有多少運氣。 )編輯:爲了澄清一點,在我的文章中,我解釋了發生的事情,而不是保證發生的事情。我想我應該在答案中澄清一下。 – Corbin

+0

現在,第一部分我明白了。但是第二部分(int&)a,我是一個混亂的人,因爲當我們定義一個引用時,我們必須初始化引用,對吧?像int &a = b;但這種情況下,如何解釋? (int&)a現在是一個整數引用,但我們不知道它引用的變量? –

2

這些值是不同的,因爲將float解釋爲int &(參考int)會使門敞開。 a不是int,所以當你這樣做的時候幾乎可以發生任何事情。碰巧,看着float就好像它是int會給你1065353216,但是根據底層機器的體系結構,它可能是42,或者是一頭粉紅色的芭蕾舞短裙,或者甚至是墜毀的大象。

請注意,這與鑄造到int不同,該工具瞭解如何將float轉換爲int。施放到int &只是查看內存中的位而不理解最初的含義。

+0

你是說這是未定義的行爲,或者僅僅是實現定義的行爲? –

+0

@OliCharlesworth我不知道他在說什麼,但標準清楚地表明這是未定義的行爲。 (該標準還清楚地表明,實現的目的是實現熟悉機器體系結構的人所期望的,某些體系結構上的哪些可能意味着某些浮點值會崩潰(我從來沒有聽說過架構然而,在那裏我期望一頭大象穿着粉紅色的短裙) –

+0

我的意思是說這是不確定的行爲,粉紅色的短裙中的大象不太可能,但是被標準允許...... –

9

這意味着未定義的行爲:-)。

說真的,這是一種類型雙關的形式。 afloat,但a也是一個內存位(通常是四個字節),其中有位。 (float&)a表示將該塊內存視爲float(換句話說,它實際上是什麼)。 (int&)a表示將其視爲int。形式上,通過具有除對象的實際類型之外的類型的左值表達式訪問對象(例如a)是未定義的行爲,除非類型是字符類型。實際上,如果兩種類型的尺寸相同,我希望結果能夠重新解釋位模式。

float的情況下,位模式包含符號位,指數位和尾數位。 通常,指數將使用一些超過-n的符號,並且只有0.0將具有0作爲指數。 (一些表示,包括PC上使用的表示,不會存儲尾數的高位,因爲在基數2的歸一化形式中,它必須始終爲1.在這種情況下,存儲的1.0的尾數將具有所有位0.)還典型地(我不知道這裏有任何例外),指數將被存儲在高位位中。結果是,當您將「浮點值」輸入爲相同大小的整數時,無論浮點值如何,該值都會相當大。

+0

但是同樣代表reinterpret_cast,因此會發生什麼是實現定義的,或者,我錯了嗎? –

+1

@VJovic在這種情況下,它是一個'reinterpret_cast'。轉換本身或多或少地被定義好(提供不違反對齊約束)。轉換在形式上是未定義的行爲(但意圖是他們做了熟悉底層架構的人所期望的)。 –