一个浮点数应该被签名,为什么减法导致一个环绕?

the*_*key 3 types objective-c type-conversion

float test=-1;
Run Code Online (Sandbox Code Playgroud)

产生float有价值的东西-1.然而,

float test=arc4random()%500-500;
Run Code Online (Sandbox Code Playgroud)

产生巨大的价值,这显然是由缓冲区溢出造成的 - 数字环绕.这不应该发生在float; 为了踢,我试图看看Xcode是否会让我做一个"签名浮动",但它告诉我"浮动无法签名或未签名."

我制作了一个解决方案int,然后将其转换为a float,但我真的很感激知道这是怎么发生的.

Cal*_*leb 10

arc4random()u_int32_t根据手册页返回a ,因此arc4random()%500-500将是无符号整数,减去500会给你一个非常大的正值.试试这个:

float test = ((float)(arc4random() % 500))-500;
Run Code Online (Sandbox Code Playgroud)

我制作了一个解决方案,我在其中制作了一个带符号的int,然后将它转换为浮点数,但我真的很感激知道这是怎么发生的.

一次看一整行.首先,你有:

arc4random()
Run Code Online (Sandbox Code Playgroud)

如上所述,它返回一个unsigned int.让我们假装它返回值12345.接下来,你有模数运算符,所以你的表达式是这样的:

12345 % 500
Run Code Online (Sandbox Code Playgroud)

也就是说345.接下来,你减去500:

345 - 500
Run Code Online (Sandbox Code Playgroud)

你认为那会给你-155,但是没有 - 我们仍然在这里的无符号整数领域工作,所以你真的得到4294967141(或类似的东西 - 我的数学可能会关闭).然后,最后,你将它分配给一个浮点数:

float test = 4294967141;
Run Code Online (Sandbox Code Playgroud)

浮点只有23位用于尾数,因此存储的值test将在4294967141的一般邻域中,但精度较低,如4294970000.