C++ 在c++;,或者只告诉编译器ok

C++ 在c++;,或者只告诉编译器ok,c++,casting,compilation,C++,Casting,Compilation,如果我有此代码: int A; unsigned int B; if (A==B) foo(); 相比之下,编译器会抱怨混合类型。如果我像这样投一个球: if ((unsigned int) A==B) foo(); 这是否指示编译器插入代码以将整型转换为无符号整型?或者它只是告诉编译器不要担心,忽略类型不匹配 更新:如果这是不安全的(如下所述),我应该如何处理这种比较?(将一个int的内容分配给一个未签名的int以供以后比较是否也不安全) 更新:哇,有一些不同的答案(来自拥有数千篇帖子的

如果我有此代码:

int A;
unsigned int B;
if (A==B) foo();
相比之下,编译器会抱怨混合类型。如果我像这样投一个球:

if ((unsigned int) A==B) foo();
这是否指示编译器插入代码以将整型转换为无符号整型?或者它只是告诉编译器不要担心,忽略类型不匹配


更新:如果这是不安全的(如下所述),我应该如何处理这种比较?(将一个int的内容分配给一个未签名的int以供以后比较是否也不安全)
更新:哇,有一些不同的答案(来自拥有数千篇帖子的人)。我已经接受了看似最好的答案,但任何阅读此问题的人都应该仔细阅读所有答案。

这取决于演员类型和你的角色。在您的特定情况下,不会发生任何事情,但在其他情况下,将执行实际代码。最简单的例子:

void foo(double d) {};
...
int x;
foo(static_cast<double>(x));
voidfoo(双d){};
...
int x;
foo(静态_-cast(x));

在本例中,将生成代码。

在强制转换时,至少在概念级别,编译器将创建强制转换表达式中指定类型的临时变量

您可以测试此表达式:

(unsigned int) A = B; // This time assignment is intended
将生成临时(常量)变量的错误指向修改


当然,编译器可以自由地优化通过强制转换创建的任何临时变量。尽管如此,必须存在一种有效的方法来构建临时模型

> P>纯类型,C和C++中,==/COD>总是用两个操作数转换为同一类型。在OP的代码中,
A
首先转换为
unsigned

如果我投。。。这是否指示编译器插入代码以将整型转换为无符号整型

是的,但那代码无论如何都会发生。如果没有强制转换,编译器只是简单地警告它将要做程序员可能不想做的事情

或者(如果我强制转换),它只是告诉编译器不要担心,忽略类型不匹配吗

类型不匹配不会被忽略。通过提供强制转换,不存在要警告的类型错误匹配


我应该如何处理这种比较

确保
A
不是负数,然后使用强制转换将其转换为
未签名的

int A;
unsigned int B;
// if (A==B) foo();
if (A >= 0 && (unsigned)A == B) foo();
每个非负的
int
都可以转换为无符号的
而不改变值

有符号整数类型的非负值范围是 相应的无符号整数类型C11dr§6.2.5 9


所以你的问题只是关于有符号/无符号比较

C++标准在第5条表达式[expr]§10中规定:

许多需要算术或枚举类型操作数的二进制运算符会导致转换并产生 结果类型以类似的方式显示。目的是生成一个公共类型,它也是结果的类型。 此模式称为常用的算术转换,其定义如下:
……
否则,如果具有无符号整数类型的操作数的秩大于或等于 另一个操作数类型的秩,有符号整数类型的操作数应转换为 具有无符号整数类型的操作数的类型

在4.7积分转换[conv.Integral]§2中

如果目标类型是无符号的,则结果值是与源相同的最小无符号整数 整数(模2n,其中n是用于表示无符号类型的位数)。[注:两分钟后 补码表示,这种转换是概念性的,位模式没有变化(如果有 没有截断)。-结束注释]

这意味着在使用2位补码表示负数、32位表示整数或无符号整数的公共系统上,
(unsigned int)-1将以4294967295结尾

它可能是你想要的或不想要的,编译器只是警告你,它会认为它们是相等的。


如果不是您想要的,只需首先测试有符号值是否为负值。如果是,则表示它们不相等,跳过相等比较。

如果需要,强制转换意味着转换。但这对于负值来说是有问题的。它们被映射到无符号类型上的正值。因此,您必须确保负值与任何(正)无符号值的比较不相等:

int A;
unsigned int B;

...

if ( (A >= 0) && (static_cast<unsigned int>(A) == B) )
    foo();
inta;
无符号整数B;
...
如果((A>=0)和&(静态(A)==B))
foo();
这是因为整数类型的无符号变量保证保存相应有符号类型的所有正值(包括
0


请注意使用了a而不是“经典”C样式转换。

如果编译器抱怨比较中存在混合类型,那么它就被破坏了。你展示的代码中没有比较:PAs@tobi303指出,你可能是指
=
,而不是你的例子中的
=
(即,相等比较,而不是赋值)。@tobi303不确定,但我相信隐藏的比较是在if,if(A)->if(A!=0)@Vladp中,实际上,当考虑它时,我还认为可能涉及到比较,但如果编译器对这段代码的比较发出警告,我会觉得很奇怪。正如Schafwolle在他的回答中所说,值只是位和字节,类型告诉编译器如何解释它们。另外,通过将值强制转换为不同的类型,该值不会改变,而转换可能必须改变值。请注意,如果
a
为负值,则无论是什么值
B
,都不会调用
foo()
B
,一种无符号类型,永远不能有负值。注意到您删除了OP的
C
标记。Meh@chux:“c++中的cast change变量”更正了编辑错误。如果您不同意,请随时回滚;在我想发布我自己的答案之前,我编辑了这篇文章