在 VC++14 中使用 std::basic_stringstream<char16_t> 时出错

Posted

技术标签:

【中文标题】在 VC++14 中使用 std::basic_stringstream<char16_t> 时出错【英文标题】:error while using std::basic_stringstream<char16_t> in VC++14 【发布时间】:2015-08-14 05:07:26 【问题描述】:

我正在尝试做一些基本的char16_t字符串(u16string)处理,但遇到了一些麻烦。这个小程序:

#include <string>
#include <sstream>

int main()

    int foo = 65;

    std::basic_stringstream<char16_t> ss;
    ss << foo;

    std::u16string s = ss.str();

产生错误:

Error   C2491   'std::numpunct<_Elem>::id': definition of dllimport static data member not allowed. xlocnum 259

我在一些在线编译器上试过这个,但没有错误。

感谢您的帮助!

【问题讨论】:

对我来说似乎是一个错误。可能与 Visual C++ 在其运行时库中附带某些标准类型的预构建版本的方式有关。它本身不是一个修复,但如果你链接到静态运行时库而不是 DLL 运行时库,代码似乎可以编译。 【参考方案1】:

好的,它看起来像是 VC++ 标准库或 VC++ 编译器中的错误,甚至可能两者兼而有之。

,第 85 行,在 class numpunct 内声明:

__PURE_APPDOMAIN_GLOBAL _CRTIMP2_PURE static locale::id id; // unique facet id

,第 258/259 行定义:

template<class _Elem>
    __PURE_APPDOMAIN_GLOBAL locale::id numpunct<_Elem>::id;

_CRTIMP2_PURE 被定义为_CRTIMP2,而_CRTIMP2 又被定义为__declspec(dllimport)

现在,根据我对 VC++ 文档的阅读,应该没问题。 __declspec(dllimport) 允许用于静态声明。但是,静态定义不允许这样做。但是定义没有__declspec(dllimport),只有声明有。

尽管如此,还是会产生错误:编译器正在查看定义,将其视为它是__declspec(dllimport),并产生错误。

我不确定是编译器错误还是库错误的原因是编译器还会发出警告,抱怨声明和定义不匹配——一个是__declspec(dllimport),另一个是不是。由于根据文档,定义不能是__declspec(dllimport),这向我建议既不声明也不定义应该是__declspec(dllimport)

如果我们看看其他类似的成员,这个怀疑就得到了证实。例如,num_get::id 不是_CRTIMP2_PURE,也不是num_put::id

所以我认为有两种可能性。一是_CRTIMP2_PURE 有误,应该将其删除。另一个是编译器在声明定义为__declspec(dllimport) 时发出错误诊断,而实际上不是。

无论哪种方式,我认为代码示例应该可以编译,这是微软需要解决的问题。

【讨论】:

很好的分析。点评:编译器没有说定义是dllimport;它说您不允许定义先前声明为dllimport 的数据成员。这是正确的:dllimport 的意思是“我会在 DLL 中找到定义,它之前(单独)使用dllexport 编译过”。为在翻译单元中声明为 dllimport 的内容提供定义没有意义,并且诊断是正确的。 它适用于charwchar_t 的原因是xlocnum 包含这些参数的显式实例化(在文件末尾)。它们看起来很奇怪,因为它们使用显式实例化的语法definitions(它们应该是extern template,而不仅仅是template),但看起来MSVC 认为它们只是声明,如果有前面的@ 987654350@ 声明(这只是一个猜测,否则它们也不会工作)。无论如何,我同意你的结论,即这需要由 MS 解决;更准确地说,在 MSVC 的标准库中。这应该报告。 哦,是的,虽然定义 dllimport 的函数是可以的,因为 dllimport 是建议性的(它是用于内联 thunk 的性能优化),我忘记了数据定义是不同的。很难确定,但看起来这实际上是一个老错误:***.com/questions/8401359/… 不过,提问者并没有提供太多细节。 你引用的代码是来自 VC++ 14 编译器吗? 你认为这是同一个错误吗? connect.microsoft.com/VisualStudio/Feedback/Details/1348277

以上是关于在 VC++14 中使用 std::basic_stringstream<char16_t> 时出错的主要内容,如果未能解决你的问题,请参考以下文章

opencv 安装 vc14可以在vs10上运行吗

opencv中vc14和vc15的区别?

为啥 vector.push_back(System::Byte) 在 VC++ 14.29 (C++/CLI) 中不再编译

VC14(VC2015)安装失败,0x80240017 - 未指定的错误,解决办法

VC14(VC2015)安装失败,0x80240017 - 未指定的错误,解决办法

VC14(VC2015)安装失败,0x80240017 - 未指定的错误,解决办法