【问题标题】:Why doesn't implicit conversion work with wide ostream?为什么隐式转换不适用于宽 ostream?
【发布时间】:2013-07-03 09:30:03
【问题描述】:

我有一些我不理解的行为。我在VS2005上观察到了这个,但是IDEONE (using GCC 4.7.2) outputs基本一样。

代码如下:

#include <iostream>
#include <string>

struct UserString {
    const char* p;
        operator const char*() const {
                std::cout << "! " << __FUNCTION__ << std::endl;
                return p;
        }

        UserString()
        : p ("UserString")
        { }
};

struct WUserString {
        const wchar_t* p;
        operator const wchar_t*() const {
                std::cout << "! " << __FUNCTION__ << std::endl;
                return p;
        }

        WUserString()
        : p (L"WUserString")
        { }
};


int main() {
        using namespace std;
        cout << "String Literal" << endl;
        cout << string("std::string") << endl;
        cout << UserString() << endl;
        cout << static_cast<const char*>(UserString()) << endl;

        wcout << L"WString Literal" << endl;
        wcout << wstring(L"std::wstring") << endl;
        wcout << WUserString() << endl;
        wcout << static_cast<const wchar_t*>(WUserString()) << endl;

        return 0;
}

这是输出:

String Literal
std::string
! operator const char*  **** "works"
UserString              ****
! operator const char*
UserString
WString Literal
std::wstring
! operator const wchar_t*  **** "doesn't" - op<<(void*) is used
0x80491b0                  ****
! operator const wchar_t*
WUserString

这是怎么回事?!?

【问题讨论】:

  • 标准 iostream 丢失。它不需要您的转换器接受指针值。你输了,因为那个更便宜。
  • @HansPassant - 您的评论没有解释为什么 charwchar_t 的行为不同。

标签: c++ operator-overloading iostream overload-resolution


【解决方案1】:

basic_ostream 有部分特化

template<class _TraitsT>
basic_ostream<char, _TraitsT>&
   operator<<(basic_ostream<char, _TraitsT>& _Stream, const char* _String);

这非常适合cout &lt;&lt; UserString() 案例。

wchar_tWUserString() 没有什么相似之处,所以成员函数

basic_ostream& operator<<(const void* _Address);

将是最好的匹配(在大多数“不寻常”的情况下)。

【讨论】:

  • 谢谢。这就解释了。您是否碰巧知道或知道为什么 char* 存在这种部分特化?这里的不对称有点烦人。
  • "unusual" 是一个很好的委婉说法 ;-) ...恕我直言,operator&lt;&lt;(const void* _Address); 更像是一个错误而不是一个功能。我认为对于我使用它的每一个案例,都有 20 个案例在运行时被它咬伤。
  • 我猜这只是历史,但我没有真正的证据。 charchar*(甚至 signed charunsigned char)还有其他几个专业化,可能被认为是一些优化的机会。
猜你喜欢
  • 2021-03-31
  • 2019-07-04
  • 1970-01-01
  • 2014-01-22
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-08-16
  • 1970-01-01
相关资源
最近更新 更多