C ++ 11:向wchar_t添加int

时间:2014-05-21 16:38:07

标签: c++11 unicode int unicode-string widechar

我天真地在wchar_t中添加了一个int,导致了Visual Studio 2013警告。

L'A' + 1 // next letter

warning C4244: 'argument' : conversion from 'int' to 'wchar_t', possible loss of data

因此,错误是将4字节的int隐式地转换为2字节的wchar_t。很公平。

C ++ 11标准的安全方法是什么?我想知道跨平台的含义,代码点的正确性和做事的可读性:L'A' + (wchar_t)1L'A' + \U1或其他什么。我的编码选项是什么?

编辑T + 2:我向黑客小组提出了这个问题。不出所料,没人理解。每个人都认为这是一个很好的面试问题,因为它非常简洁,值得进行丰富的对话。

2 个答案:

答案 0 :(得分:0)

直到我看到一个更优雅的答案,我希望有,我会采用这种模式:

(wchar_t)(L'A' + i)

我喜欢这种模式,因为i可以是负数或正数,它会按预期进行评估。如果L'A' + (wchar_t)i为否定且i未签名,则我使用wchar_t的原始概念存在缺陷。我在此假设wchar_t依赖于实现并且可以签名。

答案 1 :(得分:0)

当您将两个整数值相加时,两个值都可以放在int中,它们会被添加为int

如果您需要unsigned int以适合其中一个,则会将其添加为unsigned int s。

如果那些不够大,可以使用更大的类型。如果我记得正确(那里有一些粗糙的地方),它会变得复杂,并且会根据标准修订进行更改。

现在,如果溢出,则添加int s是未指定的。使用unsigned int s的加法保证将mod包含为2的幂。

intunsigned int转换为签名类型时,如果不符合,则结果未指定。如果它确实适合,它就适合。

如果将intunsigned int转换为无符号类型,则可以表示的值等于源mod的某个幂为2(对于给定的无符号类型是固定的)是结果。

许多流行的C ++编译器和硬件返回int的相同位模式,就像2s补码逻辑所解释的unsigned int一样,但标准并不要求这样做。

所以L'A' + 1涉及将L'A'转换为int,将1添加为int

如果我们添加遗漏位:

wchar_t bob = L'A' + 1;

我们可以看到警告发生的位置。编译器看到某人将int转换为wchar_t并向其发出警告。 (当有问题的值不是编译时常量时,这更有意义)

如果我们明确说明:

wchar_t bob = static_cast<wchar_t>(L'A' + 1);

警告(可能?希望?)消失了。只要右侧导致处于有效wchar_t值的范围内,您就是金色的。

如果您正在这样做:

wchar_t bob = static_cast<wchar_t>(L'A' + x);

其中xint,如果wchar_t已签名您可能遇到麻烦(如果x足够大,则表示未指定的结果!),如果未签名,则仍然有些惊讶。

这个static_cast方法的一个好处是,与(wchar_t)xwchar_t(x)强制转换不同,如果您不小心将指针提供给强制转换,它将无效。

请注意,转换x1相对没有意义,除非它使编译器静默,因为值始终在{{1}之前被转换(逻辑上)到int s之前操作(或+如果unsigned int是无符号且与wchar_t相同的大小)。如果int未签名,int明显大于wchar_t,则相对无害,因为后转换保证与添加wchar_t mod的功能相同两个,如果签署了wchar_t,那么无论如何都会给出一个未指定的结果。

因此,使用wchar_t投射结果。如果这不起作用,请使用位掩码明确清除您不关心的位。

最后,VS2013对static_cast使用2s补码数学。因此,intstatic_cast<wchar_t>(L'A' + x)始终生成相同的值,如果static_cast<wchar_t>( L'A' + static_cast<wchar_t>(x))替换为wchar_tunsigned short,则会生成相同的值。

这是一个糟糕的答案:它需要策展和剔除。但我很累,这可能很有启发性。