计算数据类型的范围用C [英] Calculating Ranges of Data Types in C

查看:115
本文介绍了计算数据类型的范围用C的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我通过K&放工作; R Second Edition和想不通,为什么我得到一个确定的结果。我解决问题是计算数据类型的上限和下限。具体做法是:

I'm working through K&R Second Edition, and can't figure out why I'm getting a certain result. The problem I'm solving is calculating upper and lower limits for data types. Specifically:

写一个程序来确定的char,short,int和长变量的范围,包括通过打印从标准头,并直接计算适当的值符号和无符号,哈德如果计算他们:确定的范围各种浮点类型。

"Write a program to determine the ranges of char , short , int , and long variables, both signed and unsigned , by printing appropriate values from standard headers and by direct computation. Harder if you compute them: determine the ranges of the various floating-point types."

我了解位运算符和两个的恭维,并有一个解决方案,我认为应该有符号数据类型的工作,而是它的工作无符号的数据类型而没有任何意义,我。这里的code:

I've learned about bitwise operators and two's compliment, and have a solution I think should work for signed data types, but instead it's working for unsigned data types which doesn't make any sense to me. Here's the code:

#include <stdio.h>

main()
{
    signed int i;

    i = ~0;
    i >>= 1;
    printf("Upper limit: %d\n", i);
    printf("Lower limit: %d\n", -i -1);
}

这将导致-1被打印为上限,且0打印的下限。但是,如果我改变我对一个unsigned int,我得到的结果,我期待(2147483647和-2147483648)。我不能换我解决这个的头,因为我的理解是,unsigned int可绝不会小于0,和一个符号int应该努力利用这些按位运算符,也就是说,如果它是一个32位系统,

This will result in -1 being printed for the upper limit, and 0 printed for the lower limit. However, if I change i to an unsigned int, I get the result I was expecting (2147483647 and -2147483648). I can't wrap my head around this, because my understanding is that an unsigned int can never be less than 0, and a signed int should work using these bitwise operators, ie, if it's a 32 bit system,

~0 == 11111111111111111111111111111111

~0 >> 1 == 011111111111111111111111111111111, 
           or 2147483647.

任何想法,我要去哪里错了?

Any idea where I'm going wrong?

推荐答案

输出:


  1. 注意:结果
    在EX pression I&GT;&GT; = 1 ,负值右移。 C标准说,这是一个实现定义的操作,以及许多实现定义它是算术移位。在算术移位,最显著位不变(保持MSB(符号位)= 1 )。

  1. Note:
    "In the expression i >>= 1, a negative value is shifted right. The C standard says this is an implementation-defined operation, and many implementations define it to be arithmetic shift. In an arithmetic shift, the most significant bit is unchanged (keeps MSB (signed bit) = 1)".

(你可以阅读:<一href=\"http://stackoverflow.com/questions/15729765/why-does-the-output-of-applied-on-a-negative-number-is-filled-with-ones-on-th/15730750#15730750\">Right用C转向负数的是&GT;方式&gt; 是编译器相关的其是否被烫伤或unsinfed转变,但可能你的情况做了一个算术移位)

(you can read: Right shifting negative numbers in C that >> is compiler dependent whether its singed or unsinfed shift, but probably in your case its doing an Arithmetic Shift.)

由于这个原因后,code:

For this reason after code:

 i = ~0;  
 i >>= 1;

I 遗体 0〜。这是二进制== 11111111111111111111111111111111

i remains ~0. that is in binary == 11111111111111111111111111111111.

而因为 0〜 == 11111111111111111111111111111111 是== 2'C 补1 1

And because ~0 == 11111111111111111111111111111111 is == 2'c complement of 1 that is -1.

所以,当你用打印格式字符串%d个其打印 1 。您应该使用%U 打印最大的无符号数是== 0〜

So when you prints with format string %d it print -1. You should use %u to print max unsigned value that is == ~0.

重要,这里要注意:

§6.2.6.2语言45 ,©ISO / IEC ISO / IEC 9899:201X

§6.2.6.2 Language 45, ©ISO/IEC ISO/IEC 9899:201x

(一补数)。其中哪些是适用
  实施德网络定义,因为无论是带符号位的值 1
  所有的价值为零位(对于前两个),或者用符号位和所有价值
  第1位(为一补数),是一个陷阱重新presentation还是正常
  值。在符号和幅度与一补数,如果的情况下,
  这种重presentation是正常值它被称为负零。

(ones’ complement). Which of these applies is implementation-defined, as is whether the value with sign bit 1 and all value bits zero (for the first two), or with sign bit and all value bits 1 (for ones’ complement), is a trap representation or a normal value. In the case of sign and magnitude and ones’ complement, if this representation is a normal value it is called a negative zero.

您的理解是:

〜0&GT;&GT; 1 == 011111111111111111111111111111111 是错误的! (它可能是,但在你的系统没有发生,根据输出)

~0 >> 1 == 011111111111111111111111111111111 is wrong! (it may be but not happening in your system, according to output)

〜0&GT;&GT; 1 == 111111111111111111111111111111111 ,注意MSB(签位) 1

~0 >> 1 == 111111111111111111111111111111111, note MSB(signed bit) is 1.

有关无符号的转变,尝试以下操作:

For unsigned shift, try following:

〜0U&GT;&GT; 1 == 011111111111111111111111111111111

注意后缀的 U 作为无符号。

Notice Suffix U for unsigned.

第二个printf :结果
因为 I 1 ,所以在第二个前pression -i - 1 == - (-1) - 1 == 1 - 1 == 0 所以输出为零: 0

Second printf:
Because i is -1, So in second expression -i - 1 == - (-1) - 1 == 1 - 1 == 0 so output is zero : 0.

这篇关于计算数据类型的范围用C的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆