簡體   English   中英

如果使用g ++,為什么std :: cout可轉換為void *?

[英]why is std::cout convertible to void* if using g++?

為什么一個人可以將std::ostream轉換為void指針? 我不知道std::ostream有任何這樣的轉換運算符。 下面的代碼

#include <iostream>

int main()
{
    void *p = std::cout; // why does this work? 
}

我問這個問題是因為我看到一個new的展示位置運算符被調用為

Foo* pFoo = new (std::cerr) Foo;

而且完全不知道為什么要寫這樣的東西。

PS:我正在使用帶有或不帶有-std=c++11 g ++ 4.9.2進行編譯。 clang ++ 不接受該代碼

PSS:發現由於所謂的“安全布爾問題”(請參閱​​@nicebyte的答案),在C ++ 11之前的版本中為std::ostream定義了一個void*轉換運算符,然后在C ++ 11中將其刪除。 但是,我的代碼使用g ++在C ++ 11中可以正常編譯。 不僅如此,無論我使用什么版本的標准,即使使用-std=c++98 ,clang ++都拒絕它,盡管我的理解是,如果編譯為C ++ 11之前的版本,它應該接受。

閱讀此內容 (您的問題將在最后一部分“ 安全的布爾問題 ”中回答)。

詳細說明一下,該實現定義了一個對void*的隱式轉換,該轉換是為std::cinstd::cout類的東西定義的,就像while(std::cin>>x){...}這樣的代碼可以編譯,而像int x = std::cin; 沒有。 這仍然是有問題的,因為您可以編寫示例中的內容。

C ++ 11通過引入顯式轉換來解決此問題。

一個顯式轉換運算符如下所示:

struct A {
 explicit operator B() { ... } // explicit conversion to B
};

當A明確轉換為B時,這樣的代碼將合法:

A a;
B b(a);

但是,這樣的代碼不是:

A a;
B b = a;

if(std::cin)類的構造要求將cin轉換為bool ,該標准指出,為了在特定情況下轉換有效,請使用諸如bool x(std::cin); 應該是“合法的”。 這可以通過向bool添加顯式轉換來實現。 它允許在上述情況下使用cin / cout,同時避免了諸如int x = std::cout;類的事情int x = std::cout;

有關更多信息,請參考Bjarne的頁面以及此問題

僅回答后續問題,因為nicebyte的答案非常適合原始問題。

可能是,您的gcc設置為使用libstdc ++(由於它是ABI突破性更改,因此尚未更改運算符),而您的clang設置為使用libc ++(從一開始就打算用作C + +11標准庫,並且在C ++ 98模式下不太符合標准-它提供了布爾轉換運算符,在C ++ 11中是顯式的。

我認為這是允許if (std::cout) ...而不允許隱式轉換為bool或類似的東西。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM