Bootstrap

C++ int long long double 等数据范围!

由于机型的不同,确实存在int到底是几个字节的问题。具体见下表:

     C类型            32               64
    char             1                1
    short int             2                2
    int             4                4
    long int             4                8
    long long int             8                8
    char*             4                8
    float             4                4
    double             8                8
现在给一种姿势,看看到底其数据范围是多少,在ACM竞赛中,经常会遇到数据溢出的问题,这里我们来看看int, long long的最大值是多少位的即10的多少次方,并以此我们大概能估计应该给变量定义什么样的类型 或者怎样对算式进行恒等变形(运算顺序等)而有效预防溢出问题。

在编译器MinGW的bin目录下有一个limits.h的头文件,我们可以打开发现其定义如下:

/* 
 * limits.h
 * This file has no copyright assigned and is placed in the Public Domain.
 * This file is a part of the mingw-runtime package.
 * No warranty is given; refer to the file DISCLAIMER within the package.
 *
 * Functions for manipulating paths and directories (included from io.h)
 * plus functions for setting the current drive.
 *
 * Defines constants for the sizes of integral types.
 *
 * NOTE: GCC should supply a version of this header and it should be safe to
 *       use that version instead of this one (maybe safer).
 *
 */

#ifndef _LIMITS_H_
#define _LIMITS_H_

/* All the headers include this file. */
#include <_mingw.h>

/*
 * File system limits
 *
 * TODO: NAME_MAX and OPEN_MAX are file system limits or not? Are they the
 *       same as FILENAME_MAX and FOPEN_MAX from stdio.h?
 * NOTE: PATH_MAX is the POSIX equivalent for Microsoft's MAX_PATH; the two
 *       are semantically identical, with a limit of 259 characters for the
 *       path name, plus one for a terminating NUL, for a total of 260.
 */
#define PATH_MAX	260

/*
 * Characteristics of the char data type.
 *
 * TODO: Is MB_LEN_MAX correct?
 */
#define CHAR_BIT	8
#define MB_LEN_MAX	2

#define SCHAR_MIN	(-128)
#define SCHAR_MAX	127

#define UCHAR_MAX	255

/* TODO: Is this safe? I think it might just be testing the preprocessor,
 *       not the compiler itself... */
#if	('\x80' < 0)
#define CHAR_MIN	SCHAR_MIN
#define CHAR_MAX	SCHAR_MAX
#else
#define CHAR_MIN	0
#define CHAR_MAX	UCHAR_MAX
#endif

/*
 * Maximum and minimum values for ints.
 */
#define INT_MAX		2147483647
#define INT_MIN		(-INT_MAX-1)

#define UINT_MAX	0xffffffff

/*
 * Maximum and minimum values for shorts.
 */
#define SHRT_MAX	32767
#define SHRT_MIN	(-SHRT_MAX-1)

#define USHRT_MAX	0xffff

/*
 * Maximum and minimum values for longs and unsigned longs.
 *
 * TODO: This is not correct for Alphas, which have 64 bit longs.
 */
#define LONG_MAX	2147483647L
#define LONG_MIN	(-LONG_MAX-1)

#define ULONG_MAX	0xffffffffUL

#ifndef __STRICT_ANSI__
/* POSIX wants this.  */ 
#define SSIZE_MAX LONG_MAX
#endif

#if (defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L) \
     || !defined(__STRICT_ANSI__)
/* ISO C9x macro names */
#define LLONG_MAX 9223372036854775807LL
#define LLONG_MIN (-LLONG_MAX - 1)
#define ULLONG_MAX (2ULL * LLONG_MAX + 1)
#endif

/*
 * The GNU C compiler also allows 'long long int'
 */
#if !defined(__STRICT_ANSI__) && defined(__GNUC__)

#define LONG_LONG_MAX	9223372036854775807LL
#define LONG_LONG_MIN	(-LONG_LONG_MAX-1)
#define ULONG_LONG_MAX	(2ULL * LONG_LONG_MAX + 1)

/* MSVC compatibility */
#define _I64_MIN LONG_LONG_MIN
#define _I64_MAX LONG_LONG_MAX
#define _UI64_MAX ULONG_LONG_MAX

#endif /* Not Strict ANSI and GNU C compiler */


#endif /* not _LIMITS_H_ */

测试样例:

#include <bits/stdc++.h>
using namespace std;

int main() {
    cout << INT_MIN << endl;
    cout << INT_MAX << endl;
    cout << UINT32_MAX << endl;
    cout << LONG_LONG_MAX << endl;
    cout << UINT64_MAX << endl;
    return 0;
}


输出结果:


-2147483648		
2147483647		int 10 位
4294967295		usigend int 10 位
9223372036854775807	long long 19 位
18446744073709551615	unsigned long long 20 位



可见  int 的最小值等于int的正最大值+1的相反数,这是因为0在补码的存储方式中只有一个的缘故。还有其他的数据范围,读者可自行查阅。


15! = 2004310016

(1 << 31) - 1  =  INT_MAX = 2147483647

20! = 2432902008176640000

(1 << 63) - 1 = LONG_LONG_MAX = 9223372036854775807


;